Upload codes, configure profile basic implementation
This commit is contained in:
parent
5550ccf6ce
commit
6051b80bfb
|
@ -0,0 +1,904 @@
|
|||
#!/usr/bin/env python
|
||||
#
|
||||
# Copyright 2009 Facebook
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License"); you may
|
||||
# not use this file except in compliance with the License. You may obtain
|
||||
# a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
|
||||
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
|
||||
# License for the specific language governing permissions and limitations
|
||||
# under the License.
|
||||
import os
|
||||
import re
|
||||
import os.path
|
||||
import tornado.httpserver
|
||||
import tornado.autoreload
|
||||
import tornado.ioloop
|
||||
import tornado.options
|
||||
import tornado.web
|
||||
import tornado.escape as escape
|
||||
import settings as msettings
|
||||
import madapps
|
||||
import datetime
|
||||
import random
|
||||
import csv
|
||||
import itertools
|
||||
import email.utils
|
||||
import json
|
||||
import StringIO
|
||||
from tornado.options import define, options, logging
|
||||
from tornado_addons import ozhandler
|
||||
import copy
|
||||
from collections import OrderedDict
|
||||
|
||||
|
||||
define("port", default=msettings.WEB_SERVER_PORT, help="run on the given port", type=int)
|
||||
|
||||
filteredapps=None
|
||||
filteredevals=None
|
||||
|
||||
smallgif='GIF89a\1\0\1\0\x80\xff\0\xff\xff\xff\0\0\0,\0\0\0\0\1\0\1\0\0\2\2D\1\0;'
|
||||
|
||||
viswidgetmap={
|
||||
'motionchart':'google.visualization.MotionChart',
|
||||
'table':'google.visualization.Table',
|
||||
'linechart':'google.visualization.LineChart',
|
||||
'piechart':'google.visualization.PieChart',
|
||||
'scatterchart':'google.visualization.ScatterChart',
|
||||
'intensitymap':'google.visualization.IntensityMap',
|
||||
'geomap':'google.visualization.GeoMap',
|
||||
'columnchart':'google.visualization.ColumnChart',
|
||||
'barchart':'google.visualization.BarChart',
|
||||
'areachart':'google.visualization.AreaChart',
|
||||
'annotatedtimeline':'google.visualization.AnnotatedTimeLine',
|
||||
'termcloud':'TermCloud',
|
||||
}
|
||||
|
||||
queries = {}
|
||||
|
||||
msettings.viswidgetmap=viswidgetmap
|
||||
|
||||
class Application(tornado.web.Application):
|
||||
def __init__(self):
|
||||
handlers = [
|
||||
(r"/", createUploadProfileHandler),
|
||||
(r"/upload-codes", uploadCodesHandler),
|
||||
(r"/save-config-controller", profileCreationHandler),
|
||||
(r"/download-config-controller", profileServeHandler),
|
||||
(r"/configure-profile", configureProfileHandler),
|
||||
(r"/save-profile", saveProfileHandler),
|
||||
(r"/?$", madAppBarHandler),
|
||||
(r"/[^/]+/?$", madAppHandler),
|
||||
(r"/[^/]+/.+$", madAppDataHandler)
|
||||
]
|
||||
|
||||
|
||||
settings = dict(
|
||||
template_path=os.path.join(os.path.dirname(__file__), "templates"),
|
||||
static_path=os.path.join(os.path.dirname(__file__), "static"),
|
||||
xsrf_cookies=False,
|
||||
cookie_secret=msettings.SECRET_KEY,
|
||||
login_url="/auth/login",
|
||||
debug=msettings.DEBUG
|
||||
)
|
||||
|
||||
tornado.web.Application.__init__(self, handlers, **settings)
|
||||
|
||||
def auth_callback(request, realm, username, password):
|
||||
if username==msettings.USERNAME and password == msettings.PASSWORD:
|
||||
request.user_id = 1
|
||||
return True
|
||||
else:
|
||||
return False
|
||||
|
||||
def numberOfGrantsUploaded(user_id, cookie_set):
|
||||
if cookie_set and user_id:
|
||||
file_name = "/tmp/p%s.tsv" % (user_id)
|
||||
if os.path.isfile(file_name):
|
||||
num_lines = sum(1 for line in open(file_name))
|
||||
if str(num_lines) == cookie_set:
|
||||
return num_lines
|
||||
return 0
|
||||
|
||||
def numberOfDocsUploaded(user_id):
|
||||
if user_id:
|
||||
file_name = "/tmp/docs%s.json" % (user_id)
|
||||
if os.path.isfile(file_name):
|
||||
num_lines = sum(1 for line in open(file_name))
|
||||
return num_lines
|
||||
return 0
|
||||
|
||||
class BaseHandler(ozhandler.DjangoErrorMixin, ozhandler.BasicAuthMixin, tornado.web.RequestHandler):
|
||||
def __init__(self, *args):
|
||||
tornado.web.RequestHandler.__init__(self, *args)
|
||||
if msettings.USERNAME!='':
|
||||
self.hiddenauthget=self.get
|
||||
self.get=self.authget
|
||||
if msettings.RESTRICT_IPS:
|
||||
self.hiddenget=self.get
|
||||
self.get=self.checkwhitelistget
|
||||
|
||||
def authget(self, *args):
|
||||
try:
|
||||
if self.passwordless:
|
||||
self.hiddenauthget(*args)
|
||||
return
|
||||
except:
|
||||
pass
|
||||
|
||||
if not self.get_authenticated_user(auth_callback, 'stats'):
|
||||
return False
|
||||
self.hiddenauthget(*args)
|
||||
|
||||
def checkwhitelistget(self, *args):
|
||||
if self.request.remote_ip not in msettings.RESTRICT_IP_WHITELIST:
|
||||
raise tornado.web.HTTPError(403)
|
||||
return self.hiddenget(*args)
|
||||
|
||||
def get_current_user(self):
|
||||
return 'anonymous'
|
||||
|
||||
def executequery(self, query, bindings=None):
|
||||
def latinnum(x):
|
||||
x=int(x)
|
||||
lx=""
|
||||
while x>25:
|
||||
lx+=chr( ord('A')+int(x/25) )
|
||||
x%=25
|
||||
lx+=chr(ord('A')+x)
|
||||
return lx
|
||||
|
||||
query=query.rstrip(';\n\s ')
|
||||
|
||||
try:
|
||||
origvars=msettings.madis.functions.variables
|
||||
c=msettings.Connection.cursor().execute(query, localbindings=bindings)
|
||||
except Exception, e:
|
||||
try:
|
||||
c.close()
|
||||
except:
|
||||
pass
|
||||
msettings.madis.functions.variables=origvars
|
||||
self.finish(str(e))
|
||||
if msettings.DEBUG:
|
||||
raise e
|
||||
return
|
||||
|
||||
# Schema from query's description
|
||||
try:
|
||||
schema=c.getdescription()
|
||||
except:
|
||||
c.close()
|
||||
msettings.madis.functions.variables=origvars
|
||||
self.finish()
|
||||
return
|
||||
|
||||
colnames=[]
|
||||
coltypes=[]
|
||||
|
||||
for cname, ctype in schema:
|
||||
if ctype==None:
|
||||
colnames+=[cname]
|
||||
coltypes+=[ctype]
|
||||
continue
|
||||
ctypehead3=ctype.lower()[0:3]
|
||||
if ctypehead3 in ('int', 'rea', 'flo', 'dou', 'num'):
|
||||
ctype='number'
|
||||
else:
|
||||
ctype='string'
|
||||
colnames+=[cname]
|
||||
coltypes+=[ctype]
|
||||
|
||||
try:
|
||||
firstrow=c.next()
|
||||
except StopIteration:
|
||||
c.close()
|
||||
msettings.madis.functions.variables=origvars
|
||||
self.finish()
|
||||
return
|
||||
except Exception, e:
|
||||
c.close()
|
||||
msettings.madis.functions.variables=origvars
|
||||
self.finish(str(e))
|
||||
return
|
||||
|
||||
# Merge with guessed schema from query's first row
|
||||
for cname, ctype, i in zip(colnames, coltypes, xrange(len(colnames))):
|
||||
if ctype==None:
|
||||
frtype=type(firstrow[i])
|
||||
if frtype in (int, float):
|
||||
coltypes[i]='number'
|
||||
else:
|
||||
coltypes[i]='string'
|
||||
|
||||
# Write responce's header
|
||||
response={"cols":[]}
|
||||
for name, ctype,num in zip(colnames, coltypes, xrange(len(colnames))):
|
||||
id=latinnum(num)
|
||||
response["cols"]+=[{"id":id, "label":name,"type":ctype}]
|
||||
|
||||
# Write header
|
||||
self.write(json.dumps(response, separators=(',', ':'), sort_keys=True, ensure_ascii=False)[0:-1] + ',"rows":[')
|
||||
|
||||
# Write first line
|
||||
response=json.dumps({"c":[{"v":x} for x in firstrow]}, separators=(',', ':'), sort_keys=True, ensure_ascii=False)
|
||||
self.write(response)
|
||||
|
||||
self.executequeryrow(c, msettings.madis.functions.variables)
|
||||
msettings.madis.functions.variables=origvars
|
||||
|
||||
def executequeryrow(self, cursor, vars):
|
||||
try:
|
||||
try:
|
||||
origvars=msettings.madis.functions.variables
|
||||
msettings.madis.functions.variables=vars
|
||||
buffer=StringIO.StringIO()
|
||||
while buffer.len<30000:
|
||||
buffer.write(','+json.dumps({"c":[{"v":x} for x in cursor.next()]}, separators=(',', ':'), sort_keys=True, ensure_ascii=False))
|
||||
self.write(buffer.getvalue())
|
||||
self.flush(callback=lambda : self.executequeryrow(cursor, msettings.madis.functions.variables))
|
||||
except StopIteration:
|
||||
cursor.close()
|
||||
self.finish(buffer.getvalue()+']}')
|
||||
finally:
|
||||
msettings.madis.functions.variables=origvars
|
||||
except IOError:
|
||||
msettings.madis.functions.variables=origvars
|
||||
cursor.close()
|
||||
pass
|
||||
|
||||
def serveimage(self, path, mime_type=None):
|
||||
if os.path.sep != "/":
|
||||
path = path.replace("/", os.path.sep)
|
||||
abspath = os.path.abspath(os.path.join(self.settings['static_path'], path))
|
||||
|
||||
if mime_type==None:
|
||||
mime_type='image/'+path[-3:]
|
||||
self.set_header("Content-Type", mime_type)
|
||||
|
||||
# Check the If-Modified-Since, and don't send the result if the
|
||||
# content has not been modified
|
||||
ims_value = self.request.headers.get("If-Modified-Since")
|
||||
if ims_value is not None:
|
||||
date_tuple = email.utils.parsedate(ims_value)
|
||||
if_since = datetime.datetime.fromtimestamp(time.mktime(date_tuple))
|
||||
if if_since >= modified:
|
||||
self.set_status(304)
|
||||
return
|
||||
|
||||
file = open(abspath, "rb")
|
||||
try:
|
||||
self.write(file.read())
|
||||
finally:
|
||||
file.close()
|
||||
|
||||
class HomeHandler(BaseHandler):
|
||||
def get(self):
|
||||
self.render("home.html", settings=msettings)
|
||||
|
||||
class madAppBarHandler(BaseHandler):
|
||||
def get(self):
|
||||
self.render('madappbar.html', apps=filteredapps, evals=filteredevals, settings=msettings)
|
||||
|
||||
trueset = set([1 , 'on', 'true', 'TRUE'])
|
||||
URIdemultiplex = {r"/" + msettings.APPDIRNAME + "/analyze":'projects'
|
||||
, r"/" + msettings.APPDIRNAME + "/datacitations":'datacitations'
|
||||
, r"/" + msettings.APPDIRNAME + "/classifier":'classification'
|
||||
, r"/" + msettings.APPDIRNAME + "/pdbs":'pdb'
|
||||
, r"/" + msettings.APPDIRNAME + "/interactivemining":'interactivemining'}
|
||||
|
||||
|
||||
class createUploadProfileHandler(BaseHandler):
|
||||
passwordless=True
|
||||
# When loading the page first time and every refresh
|
||||
def get(self):
|
||||
if 'data' in self.request.arguments:
|
||||
return
|
||||
elif 'reset' in self.request.arguments:
|
||||
# TODO RESET everything
|
||||
print "TODO RESET everything"
|
||||
else:
|
||||
# check if we already gave client a user_id
|
||||
user_id = self.get_secure_cookie('madgikmining')
|
||||
if not user_id:
|
||||
# give him a unique user_id
|
||||
user_id = 'user{0}'.format(datetime.datetime.now().microsecond + (random.randrange(1, 100+1) * 100000))
|
||||
self.set_secure_cookie('madgikmining', user_id)
|
||||
self.render('create_upload_profile.html', settings=msettings)
|
||||
# TODO Upload profile post
|
||||
def post(self):
|
||||
try:
|
||||
user_id = self.get_secure_cookie('madgikmining')
|
||||
if user_id is None:
|
||||
return
|
||||
if 'upload' in self.request.files:
|
||||
# get file info and body from post data
|
||||
fileinfo = self.request.files['upload'][0]
|
||||
fname = fileinfo['filename']
|
||||
extn = os.path.splitext(fname)[1]
|
||||
# must be .pdf or .json
|
||||
if extn != ".oamp":
|
||||
self.write(json.dumps({'respond': "<b style=\"color: red\">File must be .oamp compatible profile</b>"}))
|
||||
return
|
||||
# write data to physical file
|
||||
cname = "/tmp/profile{0}.oamp".format(user_id)
|
||||
fh = open(cname, 'w')
|
||||
fh.write(fileinfo['body'])
|
||||
fh.close()
|
||||
# extract data from profile file
|
||||
import sys
|
||||
sys.path.append(msettings.MADIS_PATH)
|
||||
import madis
|
||||
# get the profile database cursor
|
||||
cursor=madis.functions.Connection(cname).cursor()
|
||||
|
||||
# data to be sent
|
||||
data = {}
|
||||
# Write to csv file the grants ids
|
||||
if len([r for r in cursor.execute("SELECT name FROM sqlite_master WHERE type='table' AND name='grants'")]):
|
||||
cursor.execute("output '/tmp/p{0}.csv' select * from grants".format(user_id))
|
||||
numberOfGrants = numberOfGrantsUploaded(user_id, "puppet_value")
|
||||
self.set_secure_cookie('madgikmining_grantsuploaded', str(numberOfGrants))
|
||||
data['grants'] = numberOfGrants
|
||||
# write to json the poswords
|
||||
if len([r for r in cursor.execute("SELECT name FROM sqlite_master WHERE type='table' AND name='poswords'")]):
|
||||
results = [r for r in cursor.execute("select c1, c2 from poswords")]
|
||||
data['poswords'] = {value:key for value, key in results}
|
||||
# write to json the negwords
|
||||
if len([r for r in cursor.execute("SELECT name FROM sqlite_master WHERE type='table' AND name='negwords'")]):
|
||||
results = [r for r in cursor.execute("select c1, c2 from negwords")]
|
||||
data['negwords'] = {value:key for value, key in results}
|
||||
# write to json the filters
|
||||
if len([r for r in cursor.execute("SELECT name FROM sqlite_master WHERE type='table' AND name='filters'")]):
|
||||
results = [r for r in cursor.execute("select c1, c2 from filters")]
|
||||
data['filters'] = {value:key for value, key in results}
|
||||
cursor.close()
|
||||
self.write(json.dumps(data))
|
||||
self.finish()
|
||||
|
||||
except Exception as ints:
|
||||
self.write(json.dumps({'respond': "<b style=\"color: red\">Something went very wrong!</b>"}))
|
||||
print ints
|
||||
return
|
||||
|
||||
|
||||
class uploadCodesHandler(BaseHandler):
|
||||
passwordless=True
|
||||
# When loading the page first time and every refresh
|
||||
def get(self):
|
||||
if 'data' in self.request.arguments:
|
||||
return
|
||||
else:
|
||||
# check if we already gave client a user_id
|
||||
user_id = self.get_secure_cookie('madgikmining')
|
||||
if user_id is None:
|
||||
return
|
||||
# check if he already uploaded his grants ids and inform him via a message
|
||||
self.render('upload_codes.html', settings=msettings)
|
||||
def post(self):
|
||||
try:
|
||||
# get user id from cookie. Must have
|
||||
user_id = self.get_secure_cookie('madgikmining')
|
||||
if user_id is None:
|
||||
return
|
||||
if 'upload' in self.request.files:
|
||||
# get file info and body from post data
|
||||
fileinfo = self.request.files['upload'][0]
|
||||
fname = fileinfo['filename']
|
||||
extn = os.path.splitext(fname)[1]
|
||||
# must be .pdf or .json
|
||||
if extn != ".tsv" and extn != ".txt":
|
||||
self.write(json.dumps({'respond': "<b style=\"color: red\">File must be .tsv or .txt</b>"}))
|
||||
return
|
||||
codes = {}
|
||||
lines = fileinfo['body'].splitlines()
|
||||
for line in lines:
|
||||
columns = re.split(r'\t+', line.rstrip('\t'))
|
||||
if len(columns) and columns[0] == '':
|
||||
continue
|
||||
elif len(columns) > 1:
|
||||
codes[columns[0]] = columns[1]
|
||||
elif len(columns) == 1:
|
||||
codes[columns[0]] = ''
|
||||
# data to be sent
|
||||
data = {}
|
||||
if len(lines) == 1:
|
||||
data['error'] = "File <b>{0}</b> uploaded.<br><b>1 Code</b> loaded! <i>Please make sure that you separate each code with newline!</i>".format(fname)
|
||||
else:
|
||||
data['data'] = codes
|
||||
data['respond'] = "<b>{0} Codes</b> loaded successfully!".format(len(lines))
|
||||
self.set_secure_cookie('madgikmining_grantsuploaded', str(len(lines)))
|
||||
self.write(json.dumps(data))
|
||||
self.finish()
|
||||
elif 'concepts' in self.request.arguments and self.request.arguments['concepts'][0] != '{}':
|
||||
# write data to physical file
|
||||
cname = "/tmp/p{0}.tsv".format(user_id)
|
||||
fh = open(cname, 'w')
|
||||
concepts = json.loads(self.request.arguments['concepts'][0])
|
||||
for key, value in concepts.iteritems():
|
||||
fh.write("{0}\t{1}\n".format(key,value))
|
||||
fh.close()
|
||||
# data to be sent
|
||||
data = {}
|
||||
if len(concepts) == 0:
|
||||
data['error'] = "You have to provide at least one concept to continue"
|
||||
else:
|
||||
data['respond'] = "<b>{0} Codes</b> loaded successfully!".format(len(concepts))
|
||||
self.set_secure_cookie('madgikmining_grantsuploaded', str(len(concepts)))
|
||||
self.write(json.dumps(data))
|
||||
self.finish()
|
||||
|
||||
except Exception as ints:
|
||||
data = {}
|
||||
data['error'] = "<b style=\"color: red\">File Failed to Upload!</b>"
|
||||
self.write(json.dumps(data))
|
||||
self.finish()
|
||||
print ints
|
||||
return
|
||||
|
||||
|
||||
class configureProfileHandler(BaseHandler):
|
||||
passwordless=True
|
||||
# When loading the page first time and evry refresh
|
||||
def get(self):
|
||||
if 'data' in self.request.arguments:
|
||||
return
|
||||
else:
|
||||
# check if we already gave client a user_id
|
||||
user_id = self.get_secure_cookie('madgikmining')
|
||||
if user_id is None:
|
||||
return
|
||||
# check if he already uploaded his grants ids and inform him via a message
|
||||
self.render('configure_profile.html', settings=msettings)
|
||||
def post(self):
|
||||
try:
|
||||
# get user id from cookie. Must have
|
||||
user_id = self.get_secure_cookie('madgikmining')
|
||||
if user_id is None:
|
||||
return
|
||||
# post case where the user uploads his own documents
|
||||
if 'upload' in self.request.files:
|
||||
# get file info and body from post data
|
||||
fileinfo = self.request.files['upload'][0]
|
||||
fname = fileinfo['filename']
|
||||
extn = os.path.splitext(fname)[1]
|
||||
# data to be sent
|
||||
data = {}
|
||||
# must be .pdf, .txt or .json
|
||||
if extn != ".pdf" and extn != ".txt" and extn != ".json":
|
||||
data['error'] = "<b style=\"color: red\">File must be .pdf, .json or .txt</b>"
|
||||
return
|
||||
# write data to physical file
|
||||
cname = "/tmp/docs{0}{1}".format(user_id, extn)
|
||||
fh = open(cname, 'w')
|
||||
fh.write(fileinfo['body'])
|
||||
fh.close()
|
||||
# Convert pdf to txt and then to json format
|
||||
if extn == ".pdf":
|
||||
import subprocess as sub
|
||||
p = sub.Popen(['pdftotext', '-enc', 'UTF-8', cname],stdout=sub.PIPE,stderr=sub.PIPE)
|
||||
output, errors = p.communicate()
|
||||
if errors:
|
||||
data['error'] = "<b style=\"color: red\">Cannot convert .pdf to .txt</b>"
|
||||
return
|
||||
os.remove(cname)
|
||||
cname = "/tmp/docs{0}.txt".format(user_id)
|
||||
with open(cname, 'r') as fin:
|
||||
docData=fin.read().replace('\n', ' ')
|
||||
if len(docData)==0:
|
||||
data['error'] = "<b style=\"color: red\">Cannot convert .pdf to .txt</b>"
|
||||
return
|
||||
with open("/tmp/docs{0}.json".format(user_id), "wb") as fout:
|
||||
json.dump({"text":docData,"id":os.path.splitext(fname)[0]}, fout)
|
||||
os.remove(cname)
|
||||
# else check if txt is in correct json format
|
||||
elif extn == ".txt" or extn == ".json":
|
||||
try:
|
||||
jsonlist = []
|
||||
for line in open(cname, 'r'):
|
||||
jsonlist.append(json.loads(line))
|
||||
os.rename(cname, "/tmp/docs{0}.json".format(user_id))
|
||||
except ValueError, e:
|
||||
data['error'] = "<b style=\"color: red\">File is not in a valid json format</b>"
|
||||
os.remove(cname)
|
||||
print e
|
||||
return
|
||||
data['respond'] = "<b>File {0}</b> uploaded successfully!".format(fname)
|
||||
self.write(json.dumps(data))
|
||||
self.finish()
|
||||
# post case where the user selects form preset documents samples
|
||||
elif 'doc_sample' in self.request.arguments and self.request.arguments['doc_sample'][0] != '':
|
||||
|
||||
sample_file_name = ""
|
||||
if self.request.arguments['doc_sample'][0] == "nih_sample":
|
||||
sample_file_name = "static/nih_sample.tsv"
|
||||
elif self.request.arguments['doc_sample'][0] == "rcuk_sample":
|
||||
sample_file_name = "static/rcuk_sample.tsv"
|
||||
elif self.request.arguments['doc_sample'][0] == "arxiv_sample":
|
||||
sample_file_name = "static/arxiv_sample.tsv"
|
||||
sample_file = open(sample_file_name, 'r')
|
||||
|
||||
# write data to physical file
|
||||
cname = "/tmp/docs{0}/json".format(user_id)
|
||||
fh = open(cname, 'w')
|
||||
while 1:
|
||||
copy_buffer = sample_file.read(1048576)
|
||||
if not copy_buffer:
|
||||
break
|
||||
fh.write(copy_buffer)
|
||||
fh.close()
|
||||
|
||||
# data to be sent
|
||||
data = {}
|
||||
if len(concepts) == 0:
|
||||
data['error'] = "You have to provide at least one concept to continue"
|
||||
else:
|
||||
data['respond'] = "<b>{0} Codes</b> loaded successfully!".format(len(concepts))
|
||||
self.set_secure_cookie('madgikmining_grantsuploaded', str(len(concepts)))
|
||||
self.write(json.dumps(data))
|
||||
self.finish()
|
||||
# post case for the actual mining proccess
|
||||
else:
|
||||
# data to be sent
|
||||
data = {}
|
||||
# create positive and negative words weighted regex text
|
||||
pos_set = neg_set = conf = whr_conf = ''
|
||||
if 'poswords' in self.request.arguments and self.request.arguments['poswords'][0] != '{}':
|
||||
# construct math string for positive words matching calculation with weights
|
||||
pos_words = json.loads(self.request.arguments['poswords'][0])
|
||||
for key, value in pos_words.iteritems():
|
||||
pos_set += r'regexpcountuniquematches("(?:\b)%s(?:\b)",j2s(prev,middle,next))*%s + ' % (key,value)
|
||||
pos_set += "0"
|
||||
if 'negwords' in self.request.arguments and self.request.arguments['negwords'][0] != '{}':
|
||||
# construct math string for negative words matching calculation with weights
|
||||
neg_words = json.loads(self.request.arguments['negwords'][0])
|
||||
for key, value in neg_words.iteritems():
|
||||
neg_set += r'regexpcountuniquematches("(?:\b)%s(?:\b)",j2s(prev,middle,next))*%s - ' % (key,value)
|
||||
neg_set += "0"
|
||||
if pos_set != '' and neg_set != '':
|
||||
conf = ", ({0} - {1})".format(pos_set, neg_set)
|
||||
elif pos_set != '':
|
||||
conf = ", {0}".format(pos_set)
|
||||
elif neg_set != '':
|
||||
conf = ", -{0}".format(neg_set)
|
||||
if conf != '':
|
||||
conf += ' as conf'
|
||||
whr_conf = 'and conf>=0'
|
||||
|
||||
# get the database cursor
|
||||
cursor=msettings.Connection.cursor()
|
||||
|
||||
if numberOfDocsUploaded(user_id) != 0:
|
||||
doc_filters = "regexpr('[\n|\r]',c2,' ')"
|
||||
ackn_filters = "regexpr(\"\\'\", c2,'')"
|
||||
if 'punctuation' in self.request.arguments and self.request.arguments['punctuation'][0] == "1":
|
||||
doc_filters = 'keywords('+doc_filters+')'
|
||||
ackn_filters = 'keywords('+ackn_filters+')'
|
||||
if 'lettercase' in self.request.arguments and self.request.arguments['lettercase'][0] != '' and self.request.arguments['lettercase'][0] != 'None':
|
||||
if self.request.arguments['lettercase'][0] == 'Lowercase':
|
||||
doc_filters = 'lower('+doc_filters+')'
|
||||
ackn_filters = 'lower('+ackn_filters+')'
|
||||
elif self.request.arguments['lettercase'][0] == 'Uppercase':
|
||||
doc_filters = 'upper('+doc_filters+')'
|
||||
ackn_filters = 'upper('+ackn_filters+')'
|
||||
if 'stopwords' in self.request.arguments and self.request.arguments['stopwords'][0] == "1":
|
||||
doc_filters = 'filterstopwords('+doc_filters+')'
|
||||
ackn_filters = 'filterstopwords('+ackn_filters+')'
|
||||
list(cursor.execute("drop table if exists grantstemp"+user_id, parse=False))
|
||||
query_pre_grants = "create temp table grantstemp{0} as select stripchars(c1) as c1, case when c2 is null then null else {1} end as c2 from (setschema 'c1,c2' file '/tmp/p{0}.tsv' dialect:tsv)".format(user_id, ackn_filters)
|
||||
cursor.execute(query_pre_grants)
|
||||
list(cursor.execute("drop table if exists docs"+user_id, parse=False))
|
||||
query1 = "create temp table docs{0} as select c1, {1} as c2 from (setschema 'c1,c2' select jsonpath(c1, '$.id', '$.text') from (file '/tmp/docs{0}.json'))".format(user_id, doc_filters)
|
||||
cursor.execute(query1)
|
||||
else:
|
||||
data['error'] = "You have to provide at least one concept to continue"
|
||||
self.write(json.dumps(data))
|
||||
self.finish()
|
||||
return
|
||||
|
||||
list(cursor.execute("drop table if exists grants"+user_id, parse=False))
|
||||
# string concatenation workaround because of the special characters conflicts
|
||||
if 'wordssplitnum' in self.request.arguments and self.request.arguments['wordssplitnum'][0] != '':
|
||||
words_split = int(self.request.arguments['wordssplitnum'][0])
|
||||
if 0 < words_split and words_split <= 10:
|
||||
acknowledgment_split = r'textwindow2s(regexpr("([\-\[\]\/\{\}\(\)\*\+\?\.\\\^\$\|])", c2, "\\\1"),0,'+str(words_split)+r',0)'
|
||||
else:
|
||||
acknowledgment_split = r'"prev" as prev, regexpr("([\-\[\]\/\{\}\(\)\*\+\?\.\\\^\$\|])", c2, "\\\1") as middle, "next" as next'
|
||||
query0 = r"create temp table grants"+user_id+r' as select c1 as c3, jmergeregexp(jgroup("(?<=[\s\b])"||middle||"(?=[\s\b])")) as c4 from '+r"(setschema 'c1,prev,middle,next' select c1, "+acknowledgment_split+r' from grantstemp'+user_id+r' where (c1 or c1!="") and c2 not null) group by c1 union all select distinct c1 as c3, "(?!.*)" as c4 from grantstemp'+user_id+r" where (c1 or c1!='') and c2 is null"
|
||||
cursor.execute(query0)
|
||||
|
||||
query2 = "select c1, c3, max(confidence) as confidence from (select c1, c3, regexpcountuniquematches(c4, j2s(prev,middle,next)) as confidence {0} from (select c1, textwindow2s(c2,10,1,5) from (select * from docs{1})), (select c3, c4 from grants{1}) T where middle = T.c3 {2}) group by c1".format(conf, user_id, whr_conf)
|
||||
# query2 = "select c1, c3 {0} from (select c1, textwindow2s(c2,10,1,5) from (select * from docs{1})), (select c3 from grants{1}) T where middle = T.c3 {2}".format(conf, user_id, whr_conf)
|
||||
results = [r for r in cursor.execute(query2)]
|
||||
data['funding_info'] = [{"code": r[1]} for r in results]
|
||||
self.write(json.dumps(data))
|
||||
self.flush()
|
||||
self.finish()
|
||||
|
||||
except Exception as ints:
|
||||
data = {}
|
||||
data['error'] = "<b style=\"color: red\">File Failed to Upload!</b>"
|
||||
self.write(json.dumps(data))
|
||||
self.finish()
|
||||
print ints
|
||||
|
||||
try:
|
||||
cursor.close()
|
||||
except:
|
||||
pass
|
||||
|
||||
|
||||
class saveProfileHandler(BaseHandler):
|
||||
passwordless=True
|
||||
# When loading the page first time and evry refresh
|
||||
def get(self):
|
||||
if 'data' in self.request.arguments:
|
||||
return
|
||||
else:
|
||||
# check if we already gave client a user_id
|
||||
user_id = self.get_secure_cookie('madgikmining')
|
||||
if user_id is None:
|
||||
return
|
||||
# check if he already uploaded his grants ids and inform him via a message
|
||||
self.render('save_profile.html', settings=msettings)
|
||||
|
||||
|
||||
class profileCreationHandler(BaseHandler):
|
||||
def post(self):
|
||||
try:
|
||||
user_id = self.get_secure_cookie('madgikmining')
|
||||
if user_id is None:
|
||||
return
|
||||
|
||||
import sys
|
||||
sys.path.append(msettings.MADIS_PATH)
|
||||
import madis
|
||||
# get the database cursor
|
||||
# profile file name
|
||||
profile_file_name = "/tmp/OAMiningProfile_{0}.oamp".format(user_id)
|
||||
cursor=madis.functions.Connection(profile_file_name).cursor()
|
||||
# Create poswords table
|
||||
cursor.execute("drop table if exists poswords", parse=False)
|
||||
cursor.execute("create table poswords(c1,c2)", parse=False)
|
||||
# Create negwords table
|
||||
cursor.execute("drop table if exists negwords", parse=False)
|
||||
cursor.execute("create table negwords(c1,c2)", parse=False)
|
||||
# Create filters table
|
||||
cursor.execute("drop table if exists filters", parse=False)
|
||||
cursor.execute("create table filters(c1,c2)", parse=False)
|
||||
# Create grants table
|
||||
cursor.execute("drop table if exists grants", parse=False)
|
||||
cursor.execute("create table grants(c1)", parse=False)
|
||||
if 'poswords' in self.request.arguments and self.request.arguments['poswords'][0] != '{}':
|
||||
# construct math string for positive words matching calculation with weights
|
||||
pos_words = json.loads(self.request.arguments['poswords'][0])
|
||||
cursor.executemany("insert into poswords(c1,c2) values(?,?)",
|
||||
(
|
||||
(key, value,) for key, value in pos_words.iteritems()
|
||||
)
|
||||
)
|
||||
if 'negwords' in self.request.arguments and self.request.arguments['negwords'][0] != '{}':
|
||||
# construct math string for negative words matching calculation with weights
|
||||
neg_words = json.loads(self.request.arguments['negwords'][0])
|
||||
cursor.executemany("insert into negwords(c1,c2) values(?,?)",
|
||||
(
|
||||
(key, value,) for key, value in neg_words.iteritems()
|
||||
)
|
||||
)
|
||||
if 'filters' in self.request.arguments and self.request.arguments['filters'][0] != '{}':
|
||||
# construct math string for negative words matching calculation with weights
|
||||
filters = json.loads(self.request.arguments['filters'][0])
|
||||
cursor.executemany("insert into filters(c1,c2) values(?,?)",
|
||||
(
|
||||
(key, value,) for key, value in filters.iteritems()
|
||||
)
|
||||
)
|
||||
if numberOfGrantsUploaded(user_id, self.get_secure_cookie('madgikmining_grantsuploaded')) != 0:
|
||||
cursor.execute("insert into grants select stripchars(c1) as c1 from (file '/tmp/p{0}.csv')".format(user_id))
|
||||
cursor.close()
|
||||
|
||||
self.write(json.dumps({'respond': "File ploaded.<br><b>1 Code</b> loaded! <i>Please make sure that you separate each code with newline!</i>"}))
|
||||
|
||||
except Exception as ints:
|
||||
self.write(json.dumps({'respond': "<b style=\"color: red\">Mining profile couldn't be saved!</b>"}))
|
||||
print ints
|
||||
return
|
||||
self.finish()
|
||||
|
||||
|
||||
class profileServeHandler(BaseHandler):
|
||||
passwordless=True
|
||||
def get(self):
|
||||
try:
|
||||
user_id = self.get_secure_cookie('madgikmining')
|
||||
if user_id is None:
|
||||
return
|
||||
if 'saveprofile' in self.request.arguments:
|
||||
print "asda"
|
||||
profile_file_name = "/tmp/OAMiningProfile_{0}.oamp".format(user_id)
|
||||
buf_size = 4096
|
||||
self.set_header('Content-Type', 'application/octet-stream')
|
||||
self.set_header('Content-Disposition', 'attachment; filename=' + "OAMiningProfile_{0}.oamp".format(user_id))
|
||||
self.flush()
|
||||
with open(profile_file_name, 'r') as f:
|
||||
while True:
|
||||
data = f.read(buf_size)
|
||||
if not data:
|
||||
break
|
||||
self.write(data)
|
||||
self.finish()
|
||||
# TODO delete file after sending if needed
|
||||
|
||||
except Exception as ints:
|
||||
self.write(json.dumps({'respond': "<b style=\"color: red\">Something went very wrong!</b>"}))
|
||||
print ints
|
||||
return
|
||||
|
||||
|
||||
class madAppHandler(BaseHandler):
|
||||
def get(self):
|
||||
try:
|
||||
appname=re.match(r'.+/([^/]+)/?$', self.request.uri).groups()[0].lower()
|
||||
except AttributeError:
|
||||
raise tornado.web.HTTPError(404)
|
||||
|
||||
appobj=None
|
||||
for ap in madapps.apps:
|
||||
if ap['link']==appname:
|
||||
appobj=ap
|
||||
break
|
||||
|
||||
if appobj==None:
|
||||
raise tornado.web.HTTPError(404)
|
||||
|
||||
self.render('madappview.html', app=appobj, apps=filteredapps, evals=filteredevals, settings=msettings)
|
||||
|
||||
class madAppDataHandler(BaseHandler):
|
||||
|
||||
@tornado.web.asynchronous
|
||||
def post(self):
|
||||
try:
|
||||
appname, queryname=[x.lower() for x in re.match(r'.+/([^/]+)/(.+)$', self.request.uri).groups()]
|
||||
except AttributeError:
|
||||
raise tornado.web.HTTPError(404)
|
||||
|
||||
appobj=None
|
||||
query=''
|
||||
for ap in madapps.apps:
|
||||
if ap['link']==appname:
|
||||
if queryname in ap:
|
||||
appobj=ap
|
||||
if queryname=='query':
|
||||
query=appobj['query']
|
||||
else:
|
||||
query=appobj[queryname]['query']
|
||||
break
|
||||
|
||||
if appobj==None:
|
||||
raise tornado.web.HTTPError(404)
|
||||
|
||||
params=dict(((x.replace(' ','_'),y[0].replace('\n','')) for x,y in self.request.arguments.iteritems()) )
|
||||
self.executequery(query, params)
|
||||
|
||||
|
||||
|
||||
|
||||
def main():
|
||||
global filteredapps, filteredevals
|
||||
|
||||
def getqtext(query,params):
|
||||
query=query.strip('\n \s')
|
||||
query=escape.xhtml_escape(query)
|
||||
for i in params:
|
||||
i=i.replace(' ','_')
|
||||
query=re.sub(':'+i, '<b><i>'+escape.xhtml_escape(i)+'</i></b>', query)
|
||||
query=re.sub('$'+i, '<b><i>'+escape.xhtml_escape(i)+'</i></b>', query)
|
||||
query=re.sub('@'+i, '<b><i>'+escape.xhtml_escape(i)+'</i></b>', query)
|
||||
return query.replace("\n","<br/>")
|
||||
|
||||
def getparams(app):
|
||||
qparams=re.findall('%{(.*?)}',app['query'], re.UNICODE )
|
||||
return set(qparams)
|
||||
|
||||
def getqueries():
|
||||
query_dir = os.path.abspath(os.path.join(os.path.dirname(__file__),'queries'))
|
||||
for dir, _, files in os.walk(query_dir):
|
||||
for file in files:
|
||||
if file.endswith('.sql'):
|
||||
queries[os.path.splitext(file)[0]] = open(os.path.join(dir,file), 'r').read()
|
||||
if msettings.DEBUG:
|
||||
tornado.autoreload.watch(os.path.join(dir,file))
|
||||
|
||||
def getexamples(app):
|
||||
if "examples" not in app:
|
||||
return []
|
||||
fullexamples=[]
|
||||
if type(app["examples"])==list:
|
||||
i=0
|
||||
for el in app["examples"]:
|
||||
i+=1
|
||||
d={}
|
||||
d["name"]='ex'+str(i)
|
||||
d["paramstring"]=str(el).replace('{','').replace('}','').replace("'",'')
|
||||
d["paramarray"]=json.dumps(el)
|
||||
fullexamples.append(d)
|
||||
else:
|
||||
for el in app["examples"]:
|
||||
d={}
|
||||
d["name"]=el
|
||||
d["paramstring"]=str(app["examples"][el]).replace('{','').replace('}','').replace("'",'')
|
||||
d["paramarray"]=json.dumps(app["examples"][el])
|
||||
fullexamples.append(d)
|
||||
fullexamples.sort(key=lambda x:x["name"])
|
||||
return fullexamples
|
||||
|
||||
def processtemplate(app):
|
||||
if 'template' not in app:
|
||||
return
|
||||
|
||||
getqueries()
|
||||
|
||||
if 'initial_queries' in queries:
|
||||
try:
|
||||
list(msettings.Connection.cursor().execute(queries['initial_queries']))
|
||||
except Exception, e:
|
||||
raise Exception("Error when executing DB_INITIAL_EXECUTE:\n"+queries['initial_queries']+"\nThe error was:\n"+ str(e))
|
||||
|
||||
tornado.options.parse_command_line()
|
||||
|
||||
# Restructure applications
|
||||
logging.info('Running madApp startup scripts')
|
||||
|
||||
for app in madapps.apps:
|
||||
|
||||
app['link']=app['link'].lower()
|
||||
if "title" not in app:
|
||||
app["title"]=app['link']
|
||||
if "linktitle" not in app:
|
||||
app["linktitle"]=app["title"]
|
||||
|
||||
if 'startup' in app:
|
||||
c=msettings.Connection.cursor()
|
||||
logging.info('Running startup queries for app'+app['linktitle']+' :\n'+app['startup'])
|
||||
c.execute(app['startup'])
|
||||
c.close()
|
||||
|
||||
app["qtext"]=getqtext(app["query"], [p['name'] for p in app['params']])
|
||||
app["examples"]=getexamples(app)
|
||||
app['datavisualizations']=dict([(x,[y['visualizations']] if type(y['visualizations'])==dict else y['visualizations']) for x,y in app.iteritems() if type(y)==dict and 'query' in y])
|
||||
if 'query' in app:
|
||||
app['datavisualizations']['query']=copy.deepcopy(app['visualisations'])
|
||||
for vis in app['visualisations']:
|
||||
vis['viswidgetmap']=viswidgetmap[vis['name'].lower()]
|
||||
|
||||
logging.info('Completed madApp startup scripts')
|
||||
|
||||
filteredapps=filter(lambda x:("eval" not in x),madapps.apps)
|
||||
filteredevals=filter(lambda x:("eval" in x),madapps.apps)
|
||||
|
||||
if not msettings.DEBUG:
|
||||
sockets = tornado.netutil.bind_sockets(options.port)
|
||||
tornado.process.fork_processes(0)
|
||||
server = tornado.httpserver.HTTPServer(Application())
|
||||
# ssl_options = {
|
||||
#"certfile": os.path.join("/home/openaire/ssl/certificate.crt"),
|
||||
#"keyfile": os.path.join("/home/openaire/ssl/privateKey.key"),
|
||||
#})
|
||||
server.add_sockets(sockets)
|
||||
tornado.ioloop.IOLoop.instance().start()
|
||||
else:
|
||||
# debug case
|
||||
http_server = tornado.httpserver.HTTPServer(Application())
|
||||
http_server.bind(options.port)
|
||||
http_server.start(1)
|
||||
tornado.ioloop.IOLoop.instance().start()
|
||||
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
main()
|
|
@ -0,0 +1,480 @@
|
|||
(function(){
|
||||
|
||||
function getCookie(name) {
|
||||
var value = "; " + document.cookie;
|
||||
var parts = value.split("; " + name + "=");
|
||||
if (parts.length == 2) return parts.pop().split(";").shift();
|
||||
}
|
||||
|
||||
////////// UPLOAD FUNCTIONS
|
||||
|
||||
$( '.inputfile' ).each( function() {
|
||||
var $input = $( this ),
|
||||
$label = $input.next( 'label' ),
|
||||
labelVal = $label.html();
|
||||
|
||||
$input.on( 'change', function( e )
|
||||
{
|
||||
var fileName = '';
|
||||
|
||||
if( this.files && this.files.length > 1 )
|
||||
fileName = ( this.getAttribute( 'data-multiple-caption' ) || '' ).replace( '{count}', this.files.length );
|
||||
else if( e.target.value )
|
||||
fileName = e.target.value.split( '\\' ).pop();
|
||||
|
||||
if( fileName )
|
||||
$label.find( 'span' ).html( fileName );
|
||||
else
|
||||
$label.html( labelVal );
|
||||
});
|
||||
|
||||
// Firefox bug fix
|
||||
$input
|
||||
.on( 'focus', function(){ $input.addClass( 'has-focus' ); })
|
||||
.on( 'blur', function(){ $input.removeClass( 'has-focus' ); });
|
||||
});
|
||||
|
||||
var match_level_choice = 0;
|
||||
var advanced_options_open = 0;
|
||||
|
||||
var handleMatchLevelChoice = function() {
|
||||
$('#1-level').on('click', function( e ) {
|
||||
if (advanced_options_open) {
|
||||
UIkit.accordion($('.uk-accordion')).toggle(0, true);
|
||||
advanced_options_open = 0;
|
||||
}
|
||||
if (match_level_choice != 0) {
|
||||
console.log('#1-level');
|
||||
}
|
||||
match_level_choice = 0;
|
||||
});
|
||||
$('#2-level').on('click', function( e ) {
|
||||
if (advanced_options_open) {
|
||||
UIkit.accordion($('.uk-accordion')).toggle(0, true);
|
||||
advanced_options_open = 0;
|
||||
}
|
||||
if (match_level_choice != 1) {
|
||||
console.log('#2-level');
|
||||
}
|
||||
match_level_choice = 1;
|
||||
});
|
||||
$('#3-level').on('click', function( e ) {
|
||||
if (advanced_options_open) {
|
||||
UIkit.accordion($('.uk-accordion')).toggle(0, true);
|
||||
advanced_options_open = 0;
|
||||
}
|
||||
if (match_level_choice != 2) {
|
||||
console.log('#3-level');
|
||||
}
|
||||
match_level_choice = 2;
|
||||
});
|
||||
$('#c-level').on('click', function( e ) {
|
||||
if (advanced_options_open == 0) {
|
||||
UIkit.accordion($('.uk-accordion')).toggle(0, true);
|
||||
advanced_options_open = 1;
|
||||
}
|
||||
if (match_level_choice != 3) {
|
||||
console.log('#c-level');
|
||||
}
|
||||
});
|
||||
$('.uk-accordion').on('show', function () {
|
||||
console.log('#GG-level');
|
||||
UIkit.switcher($('#uk-switcher')).show(3);
|
||||
UIkit.switcher($('.uk-switcher')).show(3);
|
||||
advanced_options_open = 1;
|
||||
});
|
||||
$('.uk-accordion').on('hide', function () {
|
||||
console.log('#BB-level');
|
||||
UIkit.switcher($('#uk-switcher')).show(match_level_choice);
|
||||
UIkit.switcher($('.uk-switcher')).show(match_level_choice);
|
||||
advanced_options_open = 0;
|
||||
});
|
||||
|
||||
// UIkit.accordion($('.uk-accordion')).toggle(0, true);
|
||||
// UIkit.switcher($('#uk-switcher')).show(3);
|
||||
// UIkit.switcher($('.uk-switcher')).show(3);
|
||||
}
|
||||
|
||||
var count_pos = 0, count_neg = 0;
|
||||
|
||||
var updateCounter = function(is_pos){
|
||||
if (is_pos === 1) {
|
||||
$('#count-pos').text(count_pos);
|
||||
var deleteButton = $('#clear-all-pos');
|
||||
if(count_pos === 0){
|
||||
deleteButton.attr('disabled', 'disabled').addClass('disabled');
|
||||
}
|
||||
else{
|
||||
deleteButton.removeAttr('disabled').removeClass('disabled');
|
||||
}
|
||||
} else {
|
||||
$('#count-neg').text(count_neg);
|
||||
var deleteButton = $('#clear-all-neg');
|
||||
if(count_neg === 0){
|
||||
deleteButton.attr('disabled', 'disabled').addClass('disabled');
|
||||
}
|
||||
else{
|
||||
deleteButton.removeAttr('disabled').removeClass('disabled');
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
//generates a unique id
|
||||
var generateId = function(is_pos){
|
||||
if (is_pos) {
|
||||
return "positive-" + +new Date() + Math.random().toFixed(5).substring(2);
|
||||
} else {
|
||||
return "negative-" + +new Date() + Math.random().toFixed(5).substring(2);
|
||||
}
|
||||
}
|
||||
|
||||
var handleNextButton = function() {
|
||||
$('#next-button').on('click', function( e ) {
|
||||
console.log(JSON.stringify(wordsDataToArray()));
|
||||
var formData = new FormData();
|
||||
formData.append("concepts", JSON.stringify(wordsDataToArray()));
|
||||
$.ajax({
|
||||
url: "upload-codes",
|
||||
type: 'POST',
|
||||
data: formData,
|
||||
async: false,
|
||||
success: function (data) {
|
||||
console.log(JSON.parse(data).respond)
|
||||
window.location="configure-profile"
|
||||
},
|
||||
error: function (xhr, ajaxOptions, thrownError) {
|
||||
$('#file-upload-response').html('<b style=\"color: red\">File Failed to Upload!</b>'+xhr.status)
|
||||
// $('#file-uploaded')[0].checked = false;
|
||||
},
|
||||
cache: false,
|
||||
contentType: false,
|
||||
processData: false
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
var wordsDataToArray = function(is_pos) {
|
||||
// TODO
|
||||
var data = {};
|
||||
if (is_pos === 1) {
|
||||
$("#word-pos tbody tr").each(function(i, v){
|
||||
// data[i] = Array();
|
||||
// $(this).children('td').each(function(ii, vv){
|
||||
// data[i][ii] = $(this).text();
|
||||
// });
|
||||
data[$(v).find("td.phrase").text()] = $(v).find("td.weight").text();
|
||||
})
|
||||
} else {
|
||||
$("#word-neg tbody tr").each(function(i, v){
|
||||
// data[i] = Array();
|
||||
// $(this).children('td').each(function(ii, vv){
|
||||
// data[i][ii] = $(this).text();
|
||||
// });
|
||||
data[$(v).find("td.phrase").text()] = $(v).find("td.weight").text();
|
||||
})
|
||||
}
|
||||
|
||||
return data
|
||||
}
|
||||
|
||||
var clickedElement=null;
|
||||
var saveEditBox = function(element) {
|
||||
var new_val = $(".thVal").val();
|
||||
if (element.hasClass("phrase") || (new_val != '' && !isNaN(new_val) && new_val >= 0 && new_val <= 100)) {
|
||||
$(element).html($(".thVal").val().trim());
|
||||
} else {
|
||||
$(element).html(1);
|
||||
}
|
||||
}
|
||||
|
||||
var editValue = function(currentEle, value, isPhrase) {
|
||||
clickedElement = currentEle;
|
||||
$(document).off('click');
|
||||
if (isPhrase) {
|
||||
$(currentEle).html('<input class="uk-textarea thVal" style="word-break: break-word; width:100%" type="text" value="' + value + '" />');
|
||||
} else {
|
||||
$(currentEle).html('<input style="width:100%" class="thVal" type="text" value="' + value + '" />');
|
||||
}
|
||||
$(".thVal").focus();
|
||||
$(".thVal").keyup(function (event) {
|
||||
// Handle Enter key
|
||||
if (event.keyCode == 13) {
|
||||
var new_val = $(".thVal").val();
|
||||
$(currentEle).html($(".thVal").val().trim());
|
||||
if (isPhrase || (new_val != '' && !isNaN(new_val) && new_val >= 0 && new_val <= 100)) {
|
||||
$(currentEle).html($(".thVal").val().trim());
|
||||
} else {
|
||||
$(currentEle).html(1);
|
||||
}
|
||||
clickedElement = null;
|
||||
}
|
||||
// Handle Esc key
|
||||
else if (event.keyCode == 27) {
|
||||
$(currentEle).html(value);
|
||||
clickedElement = null;
|
||||
}
|
||||
});
|
||||
// Handle clicks outside editboxes
|
||||
$(document).click(function (event) {
|
||||
if($(event.target).attr('class')!="thVal") {
|
||||
saveEditBox(currentEle);
|
||||
$(document).off('click');
|
||||
clickedElement = null;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
// a fucntion to catch double click on positive and negative phrases edit boxes
|
||||
var addDoubleClick = function(element){
|
||||
$(element).click(function (event) {
|
||||
if($(event.target).attr('class')!="thVal") {
|
||||
event.stopPropagation();
|
||||
// save previous clicked box
|
||||
if (clickedElement)
|
||||
saveEditBox(clickedElement);
|
||||
var currentEle = $(this);
|
||||
var value = $(this).html();
|
||||
editValue(currentEle, value, currentEle.hasClass("phrase")?1:0);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
var removeWord = function(id, is_pos){
|
||||
var item = $('#' + id );
|
||||
|
||||
item.addClass('removed-item')
|
||||
.one('webkitAnimationEnd oanimationend msAnimationEnd animationend', function(e) {
|
||||
$(this).remove();
|
||||
});
|
||||
if (is_pos === 1) {
|
||||
count_pos--;
|
||||
} else {
|
||||
count_neg--;
|
||||
}
|
||||
};
|
||||
|
||||
var count_pos = 0, count_neg = 0;
|
||||
|
||||
var addDataToTable = function(id, content_word, content_weight, is_pos) {
|
||||
var row = '<tr id="' + id + '"><td class="phrase">' + content_word + '</td><td class="weight">' + content_weight +'</td></tr>'
|
||||
table = $('#data-table tbody');
|
||||
|
||||
// if content is correct and not empty append to table
|
||||
if(!$('#'+ id).length){
|
||||
|
||||
row = $(row).addClass('new-item');
|
||||
if (is_pos === 1) {
|
||||
$('#word-pos tbody').append(row);
|
||||
} else {
|
||||
$('#word-neg tbody').append(row);
|
||||
}
|
||||
|
||||
// add all the item's extra functionality
|
||||
var createdItem = $('#'+ id);
|
||||
// delete button
|
||||
createdItem.append($('<td />').append($('<a />', {
|
||||
"class" :"uk-icon-link",
|
||||
"uk-icon" : "icon: trash",
|
||||
"contenteditable" : "false",
|
||||
click: function(){
|
||||
var confirmation = confirm('Delete this word?');
|
||||
if(confirmation) {
|
||||
removeWord(id, is_pos);
|
||||
}
|
||||
}
|
||||
})));
|
||||
addDoubleClick($(createdItem).find("div.phrase"));
|
||||
addDoubleClick($(createdItem).find("div.weight"));
|
||||
createdItem.on('keydown', function(ev){
|
||||
if(ev.keyCode === 13) return false;
|
||||
});
|
||||
if (is_pos === 1) {
|
||||
count_pos++;
|
||||
updateCounter(1);
|
||||
} else {
|
||||
count_neg++;
|
||||
updateCounter(0);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
var handleWordsInput = function(){
|
||||
$('#word-form-pos').on('submit', function(event){
|
||||
event.preventDefault();
|
||||
var input_word = $('#text-pos');
|
||||
word = input_word.val();
|
||||
var input_weight = $('#weight-pos');
|
||||
weight = input_weight.val();
|
||||
if (word && weight){
|
||||
var id = generateId(1);
|
||||
addDataToTable(id, word, weight, 1);
|
||||
input_word.val('');
|
||||
input_weight.val('1');
|
||||
}
|
||||
});
|
||||
$('#word-form-neg').on('submit', function(event){
|
||||
event.preventDefault();
|
||||
var input_word = $('#text-neg');
|
||||
word = input_word.val();
|
||||
var input_weight = $('#weight-neg');
|
||||
weight = input_weight.val();
|
||||
if (word && weight){
|
||||
var id = generateId(0);
|
||||
addDataToTable(id, word, weight, 0);
|
||||
input_word.val('');
|
||||
input_weight.val('1');
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
var handleRunMiningButton = function() {
|
||||
$("#run-mining-btn").on('click', function( e ) {
|
||||
var formData = new FormData();
|
||||
formData.append("poswords", JSON.stringify(wordsDataToArray(1)));
|
||||
formData.append("negwords", JSON.stringify(wordsDataToArray(0)));
|
||||
formData.append("lettercase", $("#letter-case-select option:selected").text());
|
||||
formData.append("wordssplitnum", $("#word-split").val());
|
||||
formData.append("stopwords", $('#stop-words-filter').prop('checked')===true?1:0);
|
||||
formData.append("punctuation", $('#punctuation-filter').prop('checked')===true?1:0);
|
||||
filters_list = {};
|
||||
filters_list["lettercase"] = $("#letter-case-select option:selected").text();
|
||||
filters_list["wordssplitnum"] = $("#word-split").val();
|
||||
filters_list["stopwords"] = $('#stop-words-filter').prop('checked')===true?1:0;
|
||||
filters_list["punctuation"] = $('#punctuation-filter').prop('checked')===true?1:0;
|
||||
formData.append("filters", JSON.stringify(filters_list));
|
||||
$.ajax({
|
||||
url: "configure-profile",
|
||||
type: 'POST',
|
||||
data: formData,
|
||||
async: false,
|
||||
success: function (data) {
|
||||
console.log(data)
|
||||
},
|
||||
error: function (xhr, ajaxOptions, thrownError) {
|
||||
$('#file-upload-response').html('<b style=\"color: red\">File Failed to Upload!</b>'+xhr.status)
|
||||
// $('#file-uploaded')[0].checked = false;
|
||||
},
|
||||
cache: false,
|
||||
contentType: false,
|
||||
processData: false
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
var docsUploaded = function(docsNumber) {
|
||||
$("#docs-number").html(docsNumber+" documents uploaded");
|
||||
$("#docs-more-btn").show();
|
||||
$("#run-mining-btn").removeAttr("disabled");
|
||||
handleRunMiningButton();
|
||||
}
|
||||
|
||||
var handleFileUploadInput = function() {
|
||||
$("#docs-file-input").on('change', function() {
|
||||
if ($('#docs-file-input')[0].value === "") {
|
||||
window.alert("You must specify a data file to upload.");
|
||||
return false;
|
||||
}
|
||||
// var formData = new FormData();
|
||||
// formData.append("upload", $('#docs-file-input'));
|
||||
var formData = new FormData($('#docs-input-form')[0]);
|
||||
$.ajax({
|
||||
url: "configure-profile",
|
||||
type: 'POST',
|
||||
data: formData,
|
||||
async: false,
|
||||
success: function (data) {
|
||||
// TODO check for error
|
||||
$('#codes-file-upload-response').html(JSON.parse(data).respond)
|
||||
obj = JSON && JSON.parse(data).data || $.parseJSON(data).data;
|
||||
// console.log(obj);
|
||||
for (var key1 in obj) {
|
||||
if (obj.hasOwnProperty(key1)) {
|
||||
addDataToTable(generateId(), key1, obj[key1]);
|
||||
}
|
||||
}
|
||||
hideInitialDocsUploadForm();
|
||||
docsUploaded(12);
|
||||
},
|
||||
error: function (xhr, ajaxOptions, thrownError) {
|
||||
$('#codes-file-upload-response').html('<b style=\"color: red\">File Failed to Upload!</b>'+xhr.status)
|
||||
// $('#file-uploaded')[0].checked = false;
|
||||
},
|
||||
cache: false,
|
||||
contentType: false,
|
||||
processData: false
|
||||
});
|
||||
|
||||
return false;
|
||||
});
|
||||
}
|
||||
|
||||
var handleDocSampleChoice = function(btnIndex) {
|
||||
var formData = new FormData();
|
||||
if (btnIndex === 0) {
|
||||
formData.append("doc_sample", "nih_sample");
|
||||
} else if (btnIndex === 1) {
|
||||
formData.append("doc_sample", "rcuk_sample");
|
||||
} else if (btnIndex === 2) {
|
||||
formData.append("doc_sample", "arxiv_sample");
|
||||
} else {
|
||||
return false;
|
||||
}
|
||||
$.ajax({
|
||||
url: "configure-profile",
|
||||
type: 'POST',
|
||||
data: formData,
|
||||
async: false,
|
||||
success: function (data) {
|
||||
// TODO check for error
|
||||
$('#codes-file-upload-response').html(JSON.parse(data).respond)
|
||||
obj = JSON && JSON.parse(data).data || $.parseJSON(data).data;
|
||||
// console.log(obj);
|
||||
for (var key1 in obj) {
|
||||
if (obj.hasOwnProperty(key1)) {
|
||||
addDataToTable(generateId(), key1, obj[key1]);
|
||||
}
|
||||
}
|
||||
hideInitialDocsUploadForm();
|
||||
docsUploaded(12);
|
||||
},
|
||||
error: function (xhr, ajaxOptions, thrownError) {
|
||||
$('#codes-file-upload-response').html('<b style=\"color: red\">File Failed to Upload!</b>'+xhr.status)
|
||||
// $('#file-uploaded')[0].checked = false;
|
||||
},
|
||||
cache: false,
|
||||
contentType: false,
|
||||
processData: false
|
||||
});
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
var handleDocSampleButtons = function() {
|
||||
$('#nih-sample').on('click', function( e ) {
|
||||
handleDocSampleChoice(0);
|
||||
});
|
||||
$('#rcuk-sample').on('click', function( e ) {
|
||||
handleDocSampleChoice(1);
|
||||
});
|
||||
$('#arxiv-sample').on('click', function( e ) {
|
||||
handleDocSampleChoice(2);
|
||||
});
|
||||
}
|
||||
|
||||
var hideInitialDocsUploadForm = function() {
|
||||
$('#initial-docs-upload-form').hide();
|
||||
}
|
||||
|
||||
var init = function(){
|
||||
localStorage.clear();
|
||||
handleMatchLevelChoice();
|
||||
handleWordsInput();
|
||||
handleDocSampleButtons();
|
||||
handleFileUploadInput();
|
||||
handleNextButton();
|
||||
};
|
||||
|
||||
//start all
|
||||
init();
|
||||
|
||||
})();
|
|
@ -0,0 +1,237 @@
|
|||
(function(){
|
||||
|
||||
function getCookie(name) {
|
||||
var value = "; " + document.cookie;
|
||||
var parts = value.split("; " + name + "=");
|
||||
if (parts.length == 2) return parts.pop().split(";").shift();
|
||||
}
|
||||
|
||||
////////// UPLOAD FUNCTIONS
|
||||
|
||||
$( '.inputfile' ).each( function() {
|
||||
var $input = $( this ),
|
||||
$label = $input.next( 'label' ),
|
||||
labelVal = $label.html();
|
||||
|
||||
$input.on( 'change', function( e )
|
||||
{
|
||||
var fileName = '';
|
||||
|
||||
if( this.files && this.files.length > 1 )
|
||||
fileName = ( this.getAttribute( 'data-multiple-caption' ) || '' ).replace( '{count}', this.files.length );
|
||||
else if( e.target.value )
|
||||
fileName = e.target.value.split( '\\' ).pop();
|
||||
|
||||
if( fileName )
|
||||
$label.find( 'span' ).html( fileName );
|
||||
else
|
||||
$label.html( labelVal );
|
||||
});
|
||||
|
||||
// Firefox bug fix
|
||||
$input
|
||||
.on( 'focus', function(){ $input.addClass( 'has-focus' ); })
|
||||
.on( 'blur', function(){ $input.removeClass( 'has-focus' ); });
|
||||
});
|
||||
|
||||
//generates a unique id
|
||||
var generateId = function(){
|
||||
return "row-" + +new Date() + Math.random().toFixed(5).substring(2);
|
||||
}
|
||||
|
||||
var onUserStartTyping = function() {
|
||||
$("#initial-type-input").on( 'keypress', function( e ){
|
||||
$(this).css('display', 'none');
|
||||
var value = $(this).val();
|
||||
var newId = generateId();
|
||||
addDataToTable(newId, value, "");
|
||||
var currentEle = $('#'+ newId).find("td.code");
|
||||
editValue(currentEle, value, 0);
|
||||
});
|
||||
}
|
||||
|
||||
var handleAddRowButton = function() {
|
||||
$('#add-row-below').on('click', function( e ) {
|
||||
addDataToTable(generateId(), "", "");
|
||||
});
|
||||
}
|
||||
|
||||
var handleNextButton = function() {
|
||||
$('#next-button').on('click', function( e ) {
|
||||
console.log(JSON.stringify(tableDataToArray()));
|
||||
var formData = new FormData();
|
||||
formData.append("concepts", JSON.stringify(tableDataToArray()));
|
||||
$.ajax({
|
||||
url: "upload-codes",
|
||||
type: 'POST',
|
||||
data: formData,
|
||||
async: false,
|
||||
success: function (data) {
|
||||
console.log(JSON.parse(data).respond)
|
||||
window.location="configure-profile"
|
||||
},
|
||||
error: function (xhr, ajaxOptions, thrownError) {
|
||||
$('#file-upload-response').html('<b style=\"color: red\">File Failed to Upload!</b>'+xhr.status)
|
||||
// $('#file-uploaded')[0].checked = false;
|
||||
},
|
||||
cache: false,
|
||||
contentType: false,
|
||||
processData: false
|
||||
});
|
||||
});
|
||||
}
|
||||
|
||||
var tableDataToArray = function() {
|
||||
var data = {};
|
||||
$("#data-table tbody tr").each(function(i, v){
|
||||
// data[i] = Array();
|
||||
// $(this).children('td').each(function(ii, vv){
|
||||
// data[i][ii] = $(this).text();
|
||||
// });
|
||||
data[$(v).find("td.code").text()] = $(v).find("td.acknowl").text();
|
||||
})
|
||||
return data
|
||||
}
|
||||
|
||||
var clickedElement=null;
|
||||
var saveEditBox = function(element) {
|
||||
var new_val = $(".thVal").val();
|
||||
$(element).html($(".thVal").val().trim());
|
||||
}
|
||||
|
||||
var editValue = function(currentEle, value, isArea) {
|
||||
clickedElement = currentEle;
|
||||
$(document).off('click');
|
||||
if (isArea) {
|
||||
$(currentEle).html('<input class="uk-textarea thVal" style="word-break: break-word; width:100%" type="text" value="' + value + '" />');
|
||||
} else {
|
||||
$(currentEle).html('<input style="width:100%" class="thVal" type="text" value="' + value + '" />');
|
||||
}
|
||||
$(".thVal").focus();
|
||||
$(".thVal").keyup(function (event) {
|
||||
// Handle Enter key
|
||||
if (event.keyCode == 13) {
|
||||
var new_val = $(".thVal").val();
|
||||
$(currentEle).html($(".thVal").val().trim());
|
||||
clickedElement = null;
|
||||
}
|
||||
// Handle Esc key
|
||||
else if (event.keyCode == 27) {
|
||||
$(currentEle).html(value);
|
||||
clickedElement = null;
|
||||
}
|
||||
});
|
||||
// Handle clicks outside editboxes
|
||||
$(document).click(function (event) {
|
||||
if($(event.target).attr('class')!="thVal") {
|
||||
saveEditBox(currentEle);
|
||||
$(document).off('click');
|
||||
clickedElement = null;
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
// a fucntion to catch double click on positive and negative phrases edit boxes
|
||||
var addDoubleClick = function(element){
|
||||
$(element).click(function (event) {
|
||||
if($(event.target).attr('class')!="thVal") {
|
||||
event.stopPropagation();
|
||||
// save previous clicked box
|
||||
if (clickedElement)
|
||||
saveEditBox(clickedElement);
|
||||
var currentEle = $(this);
|
||||
var value = $(this).html();
|
||||
editValue(currentEle, value, currentEle.hasClass("acknowl")?1:0);
|
||||
}
|
||||
});
|
||||
}
|
||||
|
||||
var removeDataRow = function(id){
|
||||
var item = $('#' + id );
|
||||
|
||||
item.addClass('removed-item')
|
||||
.one('webkitAnimationEnd oanimationend msAnimationEnd animationend', function(e) {
|
||||
$(this).remove();
|
||||
});
|
||||
};
|
||||
|
||||
var count_table_rows = 1;
|
||||
|
||||
var addDataToTable = function(id, code, acknowledgment) {
|
||||
var row = '<tr id="' + id + '"><td>'+count_table_rows+'</td><td class="code">' + code + '</td><td class="acknowl">' + acknowledgment +'</td></tr>'
|
||||
table = $('#data-table tbody');
|
||||
|
||||
// if content is correct and not empty append to table
|
||||
$('#data-table tbody').append(row);
|
||||
|
||||
count_table_rows++;
|
||||
|
||||
// add all the item's extra functionality
|
||||
var createdItem = $('#'+ id);
|
||||
// delete button
|
||||
createdItem.append($('<td />').append($('<a />', {
|
||||
"class" :"uk-icon-link",
|
||||
"uk-icon" : "icon: trash",
|
||||
"contenteditable" : "false",
|
||||
click: function(){
|
||||
var confirmation = confirm('Delete this word?');
|
||||
if(confirmation) {
|
||||
removeDataRow(id);
|
||||
}
|
||||
}
|
||||
})));
|
||||
addDoubleClick($(createdItem).find("td.code"));
|
||||
addDoubleClick($(createdItem).find("td.acknowl"));
|
||||
createdItem.on('keydown', function(ev){
|
||||
if(ev.keyCode === 13) return false;
|
||||
});
|
||||
}
|
||||
|
||||
var handleFileUploadButton = function() {
|
||||
$("form#codes-file-input-form").submit(function(){
|
||||
if ($('#codes-file-input')[0].value === "") {
|
||||
window.alert("You must specify a data file to import.");
|
||||
return false;
|
||||
}
|
||||
var formData = new FormData($(this)[0]);
|
||||
$.ajax({
|
||||
url: "upload-codes",
|
||||
type: 'POST',
|
||||
data: formData,
|
||||
async: false,
|
||||
success: function (data) {
|
||||
// TODO check for error
|
||||
$('#codes-file-upload-response').html(JSON.parse(data).respond)
|
||||
obj = JSON && JSON.parse(data).data || $.parseJSON(data).data;
|
||||
// console.log(obj);
|
||||
for (var key1 in obj) {
|
||||
if (obj.hasOwnProperty(key1)) {
|
||||
addDataToTable(generateId(), key1, obj[key1]);
|
||||
}
|
||||
}
|
||||
},
|
||||
error: function (xhr, ajaxOptions, thrownError) {
|
||||
$('#codes-file-upload-response').html('<b style=\"color: red\">File Failed to Upload!</b>'+xhr.status)
|
||||
// $('#file-uploaded')[0].checked = false;
|
||||
},
|
||||
cache: false,
|
||||
contentType: false,
|
||||
processData: false
|
||||
});
|
||||
|
||||
return false;
|
||||
});
|
||||
}
|
||||
|
||||
var init = function(){
|
||||
localStorage.clear();
|
||||
handleFileUploadButton();
|
||||
onUserStartTyping();
|
||||
handleAddRowButton();
|
||||
handleNextButton();
|
||||
};
|
||||
|
||||
//start all
|
||||
init();
|
||||
|
||||
})();
|
|
@ -0,0 +1,205 @@
|
|||
{% extends "base_v2.html" %}
|
||||
{% block configure_profile %} class="current" {% end %}
|
||||
{% block content %}
|
||||
<title>Configure profile</title>
|
||||
|
||||
<button class="uk-close-large" type="button" uk-close></button>
|
||||
<div class="uk-container tm-toolbar custom-discover-toolbar uk-visible@m uk-container-small">
|
||||
<div class="uk-flex uk-flex-middle">
|
||||
<div class="uk-margin-auto-right">
|
||||
<div class="uk-grid-medium uk-child-width-auto uk-flex-middle uk-grid uk-grid-stack" uk-grid="margin: uk-margin-small-top">
|
||||
<div class="uk-first-column">
|
||||
<ul class="uk-subnav uk-subnav-line">
|
||||
<li><a href="#">Upload your project codes</a></li>
|
||||
<li class="custom-discover-li"><a class="router-link-active" href="#">Configure the matching proccess</a></li>
|
||||
<li><a href="#">Save matching profile</a></li>
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="uk-section uk-section-default">
|
||||
<div class="uk-container uk-container-expand">
|
||||
<div class="uk-grid-collapse uk-grid-divider uk-child-width-expand@s" uk-grid>
|
||||
<div>
|
||||
<h4>Matching configuration<span uk-icon="icon: info" title="If you want the tooltip to appear with a little delay, just add the delay option to the uk-tooltip attribute with your value in milliseconds." uk-tooltip="pos: bottom"></span></h4>
|
||||
<div class="uk-section uk-section-default">
|
||||
<div class="uk-container">
|
||||
<div uk-grid>
|
||||
<div class="uk-width-auto@m">
|
||||
<ul id="uk-switcher" class="uk-tab-left" uk-tab="connect: #component-tab-left" uk-switcher="connect: + ul; animation: uk-animation-fade">
|
||||
<li id="1-level"><a href="#">Light</a></li>
|
||||
<li id="2-level"><a href="#">Medium</a></li>
|
||||
<li id="3-level"><a href="#">Hard</a></li>
|
||||
<li id="c-level"><a href="#">Custom</a></li>
|
||||
</ul>
|
||||
</div>
|
||||
<div class="uk-width-expand@m">
|
||||
<ul id="component-tab-left" class="uk-switcher">
|
||||
<li>Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua.</li>
|
||||
<li>Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat.</li>
|
||||
<li>Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur, sed do eiusmod.</li>
|
||||
<li>Duis aute irure dolor in reprehenderit in voluptate velit esse cillum dolore eu fugiat nulla pariatur, sed do eiusmod.</li>
|
||||
</ul>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<hr>
|
||||
<ul uk-accordion id="uk-accordion">
|
||||
<li>
|
||||
<h5 class="uk-accordion-title">Advance tools <span uk-icon="icon: info" title="If you want the tooltip to appear with a little delay, just add the delay option to the uk-tooltip attribute with your value in milliseconds." uk-tooltip="pos: bottom"></span></h5>
|
||||
<div class="uk-accordion-content">
|
||||
<div class="uk-section uk-section-default">
|
||||
<div class="uk-container">
|
||||
<div class="uk-grid-collapse uk-grid-divider uk-child-width-expand@s" uk-grid>
|
||||
<div>
|
||||
<h5>Positive phrases<span uk-icon="icon: info" title="If you want the tooltip to appear with a little delay, just add the delay option to the uk-tooltip attribute with your value in milliseconds." uk-tooltip="pos: bottom"></span></h5>
|
||||
<div class="word-container">
|
||||
<header>
|
||||
<div style="width: 100%; padding: 0 0 5px 5px;">
|
||||
<div style="width: 48%; display: inline-block;">Phrase</div>
|
||||
<div style="width: 27%; display: inline-block;">Weight</div>
|
||||
</div>
|
||||
<form class="word-form" id="word-form-pos">
|
||||
<input type="text" id="text-pos" placeholder="Write a positive Word.."/>
|
||||
<input type="number" name="weight" min="0" max="100" id="weight-pos" placeholder="Weight" value="1"/>
|
||||
<input type="submit" class="btn" value="Add"/>
|
||||
</form>
|
||||
<div class="scroll_holder">
|
||||
<div class="scroller"></div>
|
||||
</div>
|
||||
</header>
|
||||
<table id="word-pos" class="uk-table uk-table-divider .uk-table-striped uk-table-hover">
|
||||
<tbody>
|
||||
</tbody>
|
||||
</table>
|
||||
<footer>
|
||||
<span class="count" id="count-pos"></span>
|
||||
<button class="btn clear-all" id="clear-all-pos">Delete All</button>
|
||||
</footer>
|
||||
</div>
|
||||
</div>
|
||||
<div>
|
||||
<h5>Negative phrases<span uk-icon="icon: info" title="If you want the tooltip to appear with a little delay, just add the delay option to the uk-tooltip attribute with your value in milliseconds." uk-tooltip="pos: bottom"></span></h5>
|
||||
<div class="word-container">
|
||||
<header>
|
||||
<div style="width: 100%; padding: 0 0 5px 5px;">
|
||||
<div style="width: 48%; display: inline-block;">Phrase</div>
|
||||
<div style="width: 27%; display: inline-block;">Weight</div>
|
||||
</div>
|
||||
<form class="word-form" id="word-form-neg">
|
||||
<input type="text" id="text-neg" placeholder="Write a positive Word.."/>
|
||||
<input type="number" name="weight" min="0" max="100" id="weight-neg" placeholder="Weight" value="1"/>
|
||||
<input type="submit" class="btn" value="Add"/>
|
||||
</form>
|
||||
<div class="scroll_holder">
|
||||
<div class="scroller"></div>
|
||||
</div>
|
||||
</header>
|
||||
<table id="word-neg" class="uk-table uk-table-divider .uk-table-striped uk-table-hover">
|
||||
<tbody>
|
||||
</tbody>
|
||||
</table>
|
||||
<footer>
|
||||
<span class="count" id="count-neg"></span>
|
||||
<button class="btn clear-all" id="clear-all-neg">Delete All</button>
|
||||
</footer>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<hr>
|
||||
<div class="uk-section uk-section-default">
|
||||
<div class="uk-container">
|
||||
<h5>Matching area size<span uk-icon="icon: info" title="If you want the tooltip to appear with a little delay, just add the delay option to the uk-tooltip attribute with your value in milliseconds." uk-tooltip="pos: bottom"></span></h5>
|
||||
</div>
|
||||
</div>
|
||||
<hr>
|
||||
<div class="uk-section uk-section-default">
|
||||
<div class="uk-container">
|
||||
<h5>Clean matching area's text<span uk-icon="icon: info" title="If you want the tooltip to appear with a little delay, just add the delay option to the uk-tooltip attribute with your value in milliseconds." uk-tooltip="pos: bottom"></span></h5>
|
||||
<div class="uk-margin uk-grid-small uk-child-width-auto" uk-grid>
|
||||
<label>N-grams length<span uk-icon="icon: info" title="If you want the tooltip to appear with a little delay, just add the delay option to the uk-tooltip attribute with your value in milliseconds." uk-tooltip="pos: bottom"></span><input type="number" name="word-split" min="0" max="10" id="word-split" placeholder="Word pairs" value="2"/></label>
|
||||
<label><input id="stop-words-filter" class="uk-checkbox" type="checkbox" checked> Remove stop words<span uk-icon="icon: info" title="If you want the tooltip to appear with a little delay, just add the delay option to the uk-tooltip attribute with your value in milliseconds." uk-tooltip="pos: bottom"></span></label>
|
||||
<label><input id="punctuation-filter" class="uk-checkbox" type="checkbox"> Remove punctuation<span uk-icon="icon: info" title="If you want the tooltip to appear with a little delay, just add the delay option to the uk-tooltip attribute with your value in milliseconds." uk-tooltip="pos: bottom"></span></label>
|
||||
<form class="uk-form-horizontal">
|
||||
<label class="uk-form-label" for="letter-case-select">Letter case convertion to<span uk-icon="icon: info" title="If you want the tooltip to appear with a little delay, just add the delay option to the uk-tooltip attribute with your value in milliseconds." uk-tooltip="pos: bottom"></span></label>
|
||||
<div class="uk-form-controls">
|
||||
<select class="uk-select" id="letter-case-select">
|
||||
<option>None</option>
|
||||
<option>Lowercase</option>
|
||||
<option>Uppercase</option>
|
||||
</select>
|
||||
</div>
|
||||
</form>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</li>
|
||||
</ul>
|
||||
<div>
|
||||
<div class="uk-container uk-container-expand">
|
||||
<div class="uk-grid-collapse uk-child-width-expand@s" uk-grid>
|
||||
<div>
|
||||
<h4>Matching results<span uk-icon="icon: info" title="If you want the tooltip to appear with a little delay, just add the delay option to the uk-tooltip attribute with your value in milliseconds." uk-tooltip="pos: bottom"></span></h4>
|
||||
</div>
|
||||
<div>
|
||||
<div class="uk-float-right">
|
||||
<span id="docs-number" class="uk-text">0 documents uploaded</span>
|
||||
<span id="docs-more-btn" class="uk-margin-small-left" uk-icon="icon: more" style="display: none;"></span>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<button id="run-mining-btn" class="uk-button uk-button-primary uk-margin-top" disabled>Run mining</button>
|
||||
</div>
|
||||
<div id="initial-docs-upload-form" class="uk-section uk-section-muted uk-margin-top uk-padding">
|
||||
<div class="uk-container">
|
||||
<div class="uk-alert-danger" uk-alert>
|
||||
<a class="uk-alert-close" uk-close></a>
|
||||
<p>No documents to test matching accuracy.</p>
|
||||
</div>
|
||||
<h4>Choose a sample of documents to load<span uk-icon="icon: info" title="If you want the tooltip to appear with a little delay, just add the delay option to the uk-tooltip attribute with your value in milliseconds." uk-tooltip="pos: bottom"></span></h4>
|
||||
<div class="uk-text-center">
|
||||
<button id="nih-sample" class="uk-button uk-width-large uk-button-primary uk-margin-small">NIH documents</button>
|
||||
<button id="rcuk-sample" class="uk-button uk-width-large uk-button-primary uk-margin-small">RCUK documents</button>
|
||||
<button id="arxiv-sample" class="uk-button uk-width-large uk-button-primary uk-margin-small">ARXIV documents</button>
|
||||
</div>
|
||||
<h4>Upload your project codes you want to match<span uk-icon="icon: info" title="If you want the tooltip to appear with a little delay, just add the delay option to the uk-tooltip attribute with your value in milliseconds." uk-tooltip="pos: bottom"></span></h4>
|
||||
<div class="test-upload uk-placeholder uk-text-center">
|
||||
<p><span uk-icon="icon: upload; ratio: 3.5"></span></p>
|
||||
<p>
|
||||
<span class="uk-text-middle">Attach documents file by dropping them here or</span>
|
||||
<div uk-form-custom>
|
||||
<form id="docs-input-form" method="post" enctype="multipart/form-data" accept-charset="UTF-8">
|
||||
<input type="file" name="upload" id="docs-file-input" class="inputfile">
|
||||
</form>
|
||||
<span class="uk-link">browse documents file</span>
|
||||
</div>
|
||||
</p>
|
||||
<p>
|
||||
<span class="uk-label uk-margin-small-right">JSON</span><span class="uk-label uk-margin-small-right">PDF</span><span class="uk-label">TXT</span>
|
||||
<span class="uk-text">file types</span>
|
||||
</p>
|
||||
<p class="uk-text-middle">Maximum 10MB upload</p>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div id="results-section" class="uk-section uk-section-default" style="display: none;">
|
||||
<div class="uk-container">
|
||||
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<script src="/static/configure-profile.js" type="text/javascript"></script>
|
||||
{% end %}
|
Loading…
Reference in New Issue