8000 Merge branch 'updates' · jstacoder/flask-ide@3dc11ff · GitHub
[go: up one dir, main page]

Skip to content

Commit 3dc11ff

Browse files
committed
Merge branch 'updates'
2 parents 57fadc3 + cdef54b commit 3dc11ff

19 files changed

+220
-86
lines changed

Procfile

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,2 +1 @@
1-
web: gunicorn -k gevent -w 4 --preload -b 0.0.0.0:$PORT flask_ide:app
2-
#web: flask_ide/start.sh
1+
web: HEROKU_POSTGRES_URI='postgres://ylcibqyodtjqxr:E8mn0ZaBVZ-Mo62AFbVbzEl4Uy@ec2-50-19-219-80.compute-1.amazonaws.com:5432/dbap54hevm3nvr' gunicorn -k gevent -w 8 --preload -b 0.0.0.0:$PORT flask_ide:app

flask_ide/admin.py

Lines changed: 39 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1,28 +1,60 @@
11
from ext import admin
22
from flask_admin import AdminIndexView,BaseView
33
from flask_admin.contrib.sqla.view import ModelView
4-
from flask_ide.core.models import Account,Server,ConnectionType
4+
from flask_ide.core.models import Account,Server,ConnectionType,UserProfile
5+
from flask_xxl.apps.auth.models import User,Role
56
from app import app
67

78
class AccountAdmin(ModelView):
89
def __init__(self,*args,**kwargs):
910
super(AccountAdmin,self).__init__(Account,*args,**kwargs)
11+
12+
def is_accessible(self):
13+
return False
1014

1115
class ServerAdmin(ModelView):
12-
16+
inline_models = (Account,)
1317

1418
def __init__(self,*args,**kwargs):
1519
super(ServerAdmin,self).__init__(Server,*args,**kwargs)
16-
17-
1820

21+
def is_accessible(self):
22+
return False
23+
1924
class ConnectionTypeAdmin(ModelView):
2025
def __init__(self,*args,**kwargs):
2126
super(ConnectionTypeAdmin,self).__init__(ConnectionType,*args,**kwargs)
27+
28+
def is_accessible(self):
29+
return False
2230

31+
class UserProfileView(ModelView):
32+
def __init__(self,*args,**kwargs):
33+
super(UserProfileView,self).__init__(UserProfile,UserProfile.session,category='Users',*args,**kwargs)
34+
35+
def is_accessible(self):
36+
return False
2337

38+
class UserView(ModelView):
39+
inline_models = (UserProfile,)
40+
def __init__(self,*args,**kwargs):
41+
super(UserView,self).__init__(User,User.session,category='Users',*args,**kwargs)
42+
43+
def is_accessible(self):
44+
return False
45+
46+
class RoleAdmin(ModelView):
47+
def __init__(self,*args,**kwargs):
48+
super(RoleAdmin,self).__init__(Role,Role.session,category='Users',*args,**kwargs)
49+
50+
def is_accessible(self):
51+
return False
52+
53+
2454

2555
with app.test_request_context():
26-
admin.add_view(AccountAdmin(Account.session))
27-
admin.add_view(ServerAdmin(Server.session))
28-
admin.add_view(ConnectionTypeAdmin(ConnectionType.session))
56+
admin.add_view(AccountAdmin(Account.session,category='Connections'))
57+
admin.add_view(ServerAdmin(Server.session,category='Connections'))
58+
admin.add_view(ConnectionTypeAdmin(ConnectionType.session,category='Connections'))
59+
admin.add_view(UserProfileView())
60+
admin.add_view(UserView())

flask_ide/app.py

Lines changed: 0 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -13,5 +13,4 @@
1313

1414
app = AppFactory(DevelopmentConfig).get_app(__name__)
1515
macro = FlaskMacro(app)
16-
from admin import admin
1716
app.jinja_env.globals['_get_navbar'] = get_navbar

flask_ide/core/__init__.py

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,11 @@
99
url_prefix='/')
1010

1111

12+
from flask_ide.core import models
1213
from . import views # flask_ide.core import views
1314
from . import errors #flask_ide.core import errors
1415

1516

17+
@core.before_app_first_request
18+
def get_conn():
19+
conn = models.ConnectionRecord()

flask_ide/core/models.py

Lines changed: 25 additions & 9 deletions
41
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,21 @@
1212
import sys
1313
import os
1414
from flask_xxl.basemodels import BaseMixin as Model
15+
from datetime import datetime
16+
from flask import request
17+
from flask_xxl.apps.auth.models import User
1518

19+
class ConnectionRecord(Model):
20+
# keep track of people connecting
21+
ip_address = Column(String(15),nullable=False)
22+
date = Column(Date,default=datetime.now)
23+
24+
def __init__(self):
25+
self.ip_address = request.remote_addr
26+
self.session.add(self)
27+
self.session.commit()
28+
29+
visitor_count = lambda: ConnectionRecord.query.count()
1630

1731
class ConnectionDict(object):
1832
pass
@@ -21,11 +35,10 @@ class Server(Model):
2135
__tablename__ = 'servers'
2236
__table_args__ = (
2337
UniqueConstraint('name','ip_address'),
24-
dict(extend_existing=True),
2538
)
2639

2740
accounts = relationship('Account',backref=backref(
28-
'server',uselist=False),lazy='dynamic')
41+
'server'),lazy='dynamic',cascade='all,delete-orphan')
2942

3043
ip_address = Column(String(20),nullable=False,unique=True)
3144
name = Column(String(255),unique=True)
@@ -37,25 +50,18 @@ def __unicode__(self):
3750

3851

3952
class Account(Model):
40-
__table_args__ = (
-
dict(extend_existing=True),
42-
)
4353

4454
username = Column(String(255),nullable=False)
4555
password = Column(String(255),nullable=False)
4656
server_id = Column(Integer,ForeignKey('servers.id'))
4757
base_dir = Column(String(255),nullable=False)
4858
last_login = Column(Date)
49-
server_id = Column(Integer,ForeignKey('servers.id'))
5059

5160
def __unicode__(self):
5261
return '{}'.format(self.username)#,self.server.name)
5362

5463

5564
class ConnectionType(Model):
56-
__table_args__ = (
57-
dict(extend_existing=True),
58-
)
5965

6066
name = Column(String(255),unique=True,nullable=False)
6167
connection_class = Column(String(255),nullable=False)
@@ -64,3 +70,13 @@ def __unicode__(self):
6470
return self.name
6571

6672

73+
class UserProfile(Model):
74+
75+
user_id = Column(Integer,ForeignKey('users.id'))
76+
user = relationship('User',backref=backref(
77+
'profile',uselist=False),single_parent=True,cascade='all,delete-orphan')
78+
79+
age = Column(Integer)
80+
date_added = Column(DateTime,default=datetime.now)
81+
description = Column(Text)
82+

flask_ide/ext.py

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -12,17 +12,20 @@
1212
from flask.ext.pagedown import PageDown
1313
#from flask.ext.script import Manager
1414
from flask.ext.alembic import Alembic
15-
from flask_admin import Admin
15+
from flask_admin import Admin,AdminIndexView
1616
from flask_macros import FlaskMacro
1717

18+
class MyIndex(AdminIndexView):
19+
def is_accessible(self):
20+
return False
1821

1922
macro = FlaskMacro()
2023
#manager = Manager()
2124
pagedown = PageDown()
2225
#db.engine.connection
2326
codemirror = CodeMirror()
2427
alembic = Alembic()
25-
admin = Admin(template_mode='bootstrap3')
28+
admin = Admin(template_mode='bootstrap3',index_view=MyIndex())
2629
# Almost any modern Flask extension has special init_app()
2730
# method for deferred app binding. But there are a couple of
2831
# popular extensions that no nothing about such use case.

flask_ide/fileviewer/handlers.py

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
from flask_ide.settings import DevelopmentConfig
22
from flask_ide.fileviewer.ssh_client import get_ssh_class
3+
from pathlib import Path
34
import os.path as op
45
import os
56

@@ -118,6 +119,10 @@ def is_dir(item):
118119
def is_file(item):
119120
return op.isfile(item) if item else False
120121

122+
@staticmethod
123+
def create_file(name):
124+
Path(name).touch()
125+
121126
@staticmethod
122127
def cur_dir():
123128
return os.getcwd()

flask_ide/fileviewer/ssh_client.py

Lines changed: 6 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -93,7 +93,7 @@ def isdir(self,f,*args,**kwargs):
9393
def listdir(self,name='.'):
9494
add_ = lambda itm: os.path.join(itm[0],itm[1])
9595
# #rtn = a + b if a.endswith('/') else os.path.join(a,b)
96-
# #return os.path.join(itm[0],itm[1])
96+
# #return os.path.join(itm[0],itm[1])
9797
if self.is_dir(name):
9898
res = self._sftp.listdir(name)
9999
if name != '.':
@@ -136,10 +136,9 @@ def filter_files(files):
136136
end = f.split('.')[-1]
137137
if end in IGNORE_EXTENSIONS:
138138
pass
139-
else:
139+
else:
140140
rtn.append((op.basename(f),op.relpath(f)))
141141
return rtn
142-
143142

144143
def list_dir(self,d):
145144
try:
@@ -153,7 +152,7 @@ def list_dir(self,d):
153152
return rtn
154153
except:
155154
pass
156-
155+
157156

158157
def is_dir(self,d):
159158
return self.ssh.isdir(self.base_dir + ('/' if not self.base_dir.endswith('/') else '') + d)
@@ -195,7 +194,7 @@ class _SSH(object):
195194
@classmethod
196195
def split_files_and_dirs(cls,name):
197196
return cls._conn.split_files_and_dirs(name)
198-
197+
199198
@classmethod
200199
def is_dir(cls,name):
201200
return cls._conn.is_dir(name)
@@ -261,7 +260,7 @@ def _sftp():
261260
sleep(5)
262261
sftp = get_sftp(rtn)
263262
return sftp
264-
263+
265264
def _get_mode(_conn,fname):
266265
cmd = "stat --format=%f {}".format(fname)
267266
print 'executing',cmd
@@ -293,12 +292,11 @@ def dir_name(item,conn):
293292
cmd = 'python -c "import os; print os.path.dirname(os.path.abspath('+repr(item)+'))"'
294293
i,o,e = conn.exec_command(cmd)
295294
return o.read().strip()
296-
297295

298296
def listdir(conn,name='.'):
299297
add_ = lambda itm: os.path.join(itm[0],itm[1])
300298
# #rtn = a + b if a.endswith('/') else os.path.join(a,b)
301-
# #return os.path.join(itm[0],itm[1])
299+
# #return os.path.join(itm[0],itm[1])
302300
if is_dir(name):
303301
res = self._sftp.listdir(name)
304302
if name != '.':
@@ -309,7 +307,6 @@ def listdir(conn,name='.'):
309307
rtn = name
310308
return rtn
311309

312-
313310
def main():
314311
if len(sys.argv) > 1:
315312
dirname = sys.argv[1]

flask_ide/fileviewer/templates/file_editor.html

Lines changed: 28 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -36,8 +36,7 @@
3636
{% set fp = '' %}
3737
{% for path in data.split('/') %}
3838
{% set fp = fp + path + '/' %}
39-
<li{% if loop.last -%}
40-
class="active"
39+
<li{% if loop.last %} class="active"
4140
{%- endif %}>
4241
{%- if not loop.last -%}
4342
<a href="{{url_for('fileviewer.view_files',item_name=fp)}}">
@@ -56,7 +55,7 @@
5655
{%- if not loop.last and not name == '' -%}
5756
/
5857
{%- endif -%}
59-
{%- endfor %}
58+
{%- endfor -%}
6059
{% endmacro %}
6160
{% macro get_parent_link() %}
6261
{% set name = make_parent_path(request.args.get('item_name','/').split('/')[:-1]).strip() %}
@@ -78,7 +77,6 @@
7877
{{ url_for('fileviewer.view_files',item_name=path) }}
7978
{% endfor %}
8079
{% endmacro %}
81-
8280
{% block header %}
8381
{% include _get_navbar('bootstrap-inverse') with context %}
8482
{% endblock %}
@@ -87,12 +85,16 @@
8785
{{ codemirror.include_codemirror() }}
8886
{% endif %}
8987
<style>
90-
#body .well,#body .panel {
91-
box-shadow: 5px 9px 15px rgba(0, 0, 0, 0.32);
92-
}
93-
}
94-
.navbar-left { min-width:420px;}
95-
#fs { margin-top:-45px;}
88+
#body .well,
89+
#body .panel {
90+
box-shadow: 5px 9px 15px rgba(0, 0, 0, 0.32);
91+
}
92+
.navbar-left {
93+
min-width:420px;
94+
}
95+
#fs {
96+
margin-top:-45px;
97+
}
9698
#fs > fs { font-size:20px;}
9799
.list-group-item {
98100
padding:0px 30px;
@@ -278,12 +280,26 @@ <h4 class="modal-title" id="myModalLabel">Confirm Save Action</h4>
278280
$.getJSON('/view_files/msgs',{}).success(function(data){
279281
console.log(data.result.trim().split('<//>'));
280282
$(data.result.trim().split('<//>')[0]).insertAfter($(".navbar"));
281-
var closer = function(seconds){ setTimeout(function(){$(".alert").alert('close');},seconds*1000);};
283+
var closer = function(seconds){
284+
setTimeout(
285+
function(){
286+
$(".alert").alert('close');
287+
},seconds*1000);
288+
};
282289
closer(3);
283290
});
284291
$("#myModal").modal("hide");
285292
} else {
286-
$("<form>").attr("action","{{ url_for('.view_files',item_name=parent_path()) }}").attr("method","GET").submit();
293+
$("<form>")
294+
.attr(
295+
"action",
296+
"{{ url_for('.view_files',item_name=parent_path()) }}"
297+
)
298+
.attr(
299+
"method",
300+
"GET"
301+
)
302+
.submit();
287303
}
288304
}
289305
});

flask_ide/fileviewer/templates/messages.html

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
{% macro flashed_msg(msg,cat) %}
22
<div class="alert alert-{{ cat }} alert-dismissible" role="alert">
33
<button type="button" class="close" data-dismiss="alert" aria-label="Close"><span aria-hidden="true">&times;</span></button>
4-
<strong>{{ msg }}
4+
<strong>{{ msg }}</strong>
55
</div>
66
{% endmacro %}
77

@@ -14,4 +14,4 @@
1414
{% endif %}
1515
{% endfor %}
1616
{% endif %}
17-
{% endwith %}
17+
{% endwith %}

0 commit comments

Comments
 (0)
0