defaults in PAuser include noo/folders for import/storage separated, defaults are stored into PAUser in DB, changable in GUI, used as the defaults for new PA_User_States. Also disabled search noo, search folders as they are hard-coded in the ORM retreive anyway

This commit is contained in:
2022-01-22 23:26:14 +11:00
parent 0f4632e240
commit 2e4b1ed9d2
8 changed files with 75 additions and 45 deletions

2
BUGs
View File

@@ -1,3 +1,5 @@
### Next: 81 ### Next: 81
BUG-56: when making a viewing list of AI:mich, (any search?) and going past the page_size, it dies BUG-56: when making a viewing list of AI:mich, (any search?) and going past the page_size, it dies
BUG-60: entries per page in flat view will get how_many from each top-level dir in PATH (not a big issue, but it is a little misleading) BUG-60: entries per page in flat view will get how_many from each top-level dir in PATH (not a big issue, but it is a little misleading)
BUg-81: search for AI:mich, she is matched twice in a montage image, and so 2 faces, 1 file -- means the next button is disabled as it uses basic logic of # of photos to display < how_many (so get 10 matches from DB, but only show 9 files with how_many 10) -- next is then disabled
- could get actual last (and first) eid and store it in pa_user_state

9
TODO
View File

@@ -1,10 +1,7 @@
## GENERAL ## GENERAL
* for below.. make Options( request ) * for below.. make Options( request )
- remove all "Options()" that are not set by a user-choice in the F/E and just make sure new "Options" sets all defaults as needed - remove all "Options()" that are not set by a user-choice in the F/E and just make sure new "Options" sets all defaults as needed
- in fact if we "re-use" a pa_user_state, we need to update it with anything that changed -- not sure but that should just happen in State() - some done, just finish it
- use prefs in States() for defaults, rather than hardcoding "50", etc.
- search allows folder/flat change in GUI, should disable it
- search NOO -- no code to handle noo!!!
* going forward into search page (and probably all POSTs) does not work -- use POST -> redirect to GET * going forward into search page (and probably all POSTs) does not work -- use POST -> redirect to GET
/viewlist ? -> think it works, BUT, need a rewrite anyway to use json data rather than new urls... /viewlist ? -> think it works, BUT, need a rewrite anyway to use json data rather than new urls...
@@ -14,6 +11,10 @@
files.py:@app.route("/fix_dups", methods=["POST"]) files.py:@app.route("/fix_dups", methods=["POST"])
??? ???
* delete / rescan in dev, needs to delete faces, frl, ffl, ...
* search allow noo?
* optim to not run_ai_on_* for scan, needs to make sure last run_ai_on actually ran/worked - might have failed (or in my case was marked stale and I cancelled it) * optim to not run_ai_on_* for scan, needs to make sure last run_ai_on actually ran/worked - might have failed (or in my case was marked stale and I cancelled it)
-- also the case for get file details though, need to make sure last one was completed -- also the case for get file details though, need to make sure last one was completed

View File

@@ -92,7 +92,7 @@ def save_user(dn, username, data, memberships):
# if we already have a valid user/session, and say the web has restarted, just re-use it, dont make more users # if we already have a valid user/session, and say the web has restarted, just re-use it, dont make more users
if pau: if pau:
return pau return pau
pau=PAUser(dn=dn, default_noo="Oldest", default_grouping="None", default_how_many=50, default_size=128, default_folders=True, default_fullscreen=False) pau=PAUser(dn=dn, default_import_noo="Oldest", default_storage_noo="A to Z", default_grouping="None", default_how_many=50, default_size=128, default_import_folders=False, default_storage_folders=True, default_fullscreen=False)
db.session.add(pau) db.session.add(pau)
db.session.commit() db.session.commit()
return pau return pau

View File

@@ -56,15 +56,12 @@ class States(PA):
base=request.base_url base=request.base_url
base=base.replace("ChangeFileOpts", "") base=base.replace("ChangeFileOpts", "")
self.url = "/"+ref.replace(base, "" ) self.url = "/"+ref.replace(base, "" )
print( f"started with ChangeFileOpts, so self.url now is {self.url}, bu={request.base_url}")
# if viewlist, then we really are a view, and view_eid should be in the form # if viewlist, then we really are a view, and view_eid should be in the form
if 'viewlist' in request.path: if 'viewlist' in request.path:
self.path_type = 'View' self.path_type = 'View'
self.view_eid = request.form['view_eid'] self.view_eid = request.form['view_eid']
self.url = request.form['orig_url'] self.url = request.form['orig_url']
for el in request.form:
print( f"{el}={request.form[el]}" )
# this occurs ONLY when a POST to /view/<id> occurs (at this stage orig_url will be from an import, storage, bin or search) # this occurs ONLY when a POST to /view/<id> occurs (at this stage orig_url will be from an import, storage, bin or search)
elif 'view' in request.path: elif 'view' in request.path:
self.path_type = 'View' self.path_type = 'View'
@@ -77,7 +74,6 @@ class States(PA):
# from pref # from pref
pref=PA_UserState.query.filter(PA_UserState.pa_user_dn==current_user.dn,PA_UserState.path_type==self.path_type,PA_UserState.view_eid==self.view_eid).first() pref=PA_UserState.query.filter(PA_UserState.pa_user_dn==current_user.dn,PA_UserState.path_type==self.path_type,PA_UserState.view_eid==self.view_eid).first()
self.url = pref.orig_url self.url = pref.orig_url
print( f"view/ so change url to: '{self.url}'" )
print( f"NOW, url={self.url}" ) print( f"NOW, url={self.url}" )
@@ -103,7 +99,6 @@ class States(PA):
# okay if we are a search, but came from a view then get last_search_state form prefs and use it # okay if we are a search, but came from a view then get last_search_state form prefs and use it
self.orig_search_term = self.url[8:] self.orig_search_term = self.url[8:]
if self.path_type == "View": if self.path_type == "View":
print(f"view, url={self.url}")
self.orig_ptype = 'Search' self.orig_ptype = 'Search'
self.orig_url = self.url self.orig_url = self.url
else: else:
@@ -113,21 +108,13 @@ class States(PA):
self.view_eid = self.url[6:] self.view_eid = self.url[6:]
self.path_type="View" self.path_type="View"
self.orig_url=self.url self.orig_url=self.url
print( f"in view, eid={self.view_eid}, orig_url={self.orig_url}" ) elif 'ChangeFileOpts' not in self.url:
elif 'ChangeFileOpts' in self.url:
print( f"ChangeFileOpts called, so all good?" )
else:
print( f"referrer={request.referrer}" )
print( f"ERROR: DDP messed up, failed to match URL {self.url} for settings this will fail, redirecting to home" ) print( f"ERROR: DDP messed up, failed to match URL {self.url} for settings this will fail, redirecting to home" )
print( f"referrer={request.referrer}" )
return return
if self.path_type == 'View': if self.path_type == 'View':
print( f"its is a view, find the pref: {self.view_eid}" )
pref=PA_UserState.query.filter(PA_UserState.pa_user_dn==current_user.dn,PA_UserState.path_type==self.path_type,PA_UserState.view_eid==self.view_eid).first() pref=PA_UserState.query.filter(PA_UserState.pa_user_dn==current_user.dn,PA_UserState.path_type==self.path_type,PA_UserState.view_eid==self.view_eid).first()
if not pref:
print( f"no pref" )
else:
print( f"pref={pref}" )
elif self.path_type == 'Search': elif self.path_type == 'Search':
pref=PA_UserState.query.filter(PA_UserState.pa_user_dn==current_user.dn,PA_UserState.path_type==self.path_type,PA_UserState.orig_search_term==self.orig_search_term).first() pref=PA_UserState.query.filter(PA_UserState.pa_user_dn==current_user.dn,PA_UserState.path_type==self.path_type,PA_UserState.orig_search_term==self.orig_search_term).first()
else: else:
@@ -147,16 +134,30 @@ class States(PA):
self.orig_url = pref.orig_url self.orig_url = pref.orig_url
self.view_eid = pref.view_eid self.view_eid = pref.view_eid
else: else:
self.folders=False # retreive defaults from 'PAUser' where defaults are stored
self.noo="Oldest" u=PAUser.query.filter(PAUser.dn==current_user.dn).one()
self.grouping="None" self.grouping=u.default_grouping
self.how_many="50" self.how_many=u.default_how_many
self.offset="0" self.offset="0"
self.size="128" self.size=u.default_size
if self.path_type == "View": if self.path_type == "View":
self.root='static/' + self.orig_ptype self.root='static/' + self.orig_ptype
tmp=self.orig_ptype
else: else:
self.root='static/' + self.path_type self.root='static/' + self.path_type
tmp=self.path_type
if tmp == 'Import':
self.noo = u.default_import_noo
self.folders = u.default_import_folders
elif tmp == 'Storage':
self.noo = u.default_storage_noo
self.folders = u.default_storage_folders
else:
# is a search so...
print( "For now, search defaults for noo / folders are hardcoded" )
self.folders=False
self.noo = 'Oldest'
self.cwd=self.root self.cwd=self.root
if not hasattr(self, 'orig_ptype'): if not hasattr(self, 'orig_ptype'):
self.orig_ptype=None self.orig_ptype=None
@@ -206,12 +207,14 @@ class States(PA):
if 'next' in request.form: if 'next' in request.form:
self.offset += int(self.how_many) self.offset += int(self.how_many)
# now save pref (if this is 'another' search, view, etc. then it will add a row for it with matching search_term, or view_eid, etc. # now save pref
if not pref: if not pref:
# insert new pref for this combo (might be a new search or view, or first time for a path)
pref=PA_UserState( pa_user_dn=current_user.dn, path_type=self.path_type, view_eid=self.view_eid, noo=self.noo, grouping=self.grouping, how_many=self.how_many, pref=PA_UserState( pa_user_dn=current_user.dn, path_type=self.path_type, view_eid=self.view_eid, noo=self.noo, grouping=self.grouping, how_many=self.how_many,
st_offset=self.offset, size=self.size, folders=self.folders, root=self.root, cwd=self.cwd, st_offset=self.offset, size=self.size, folders=self.folders, root=self.root, cwd=self.cwd,
orig_ptype=self.orig_ptype, orig_search_term=self.orig_search_term, orig_url=self.orig_url ) orig_ptype=self.orig_ptype, orig_search_term=self.orig_search_term, orig_url=self.orig_url )
else: else:
# update this pref with the values calculated above (most likely from POST to form)
pref.pa_user_dn=current_user.dn pref.pa_user_dn=current_user.dn
pref.path_type=self.path_type pref.path_type=self.path_type
pref.view_eid=self.view_eid pref.view_eid=self.view_eid

View File

@@ -18,11 +18,13 @@ create table SETTINGS(
create table PA_USER( create table PA_USER(
ID integer, ID integer,
DN varchar unique, DN varchar unique,
DEFAULT_NOO varchar, DEFAULT_IMPORT_NOO varchar,
DEFAULT_STORAGE_NOO varchar,
DEFAULT_GROUPING varchar(16), DEFAULT_GROUPING varchar(16),
DEFAULT_HOW_MANY integer, DEFAULT_HOW_MANY integer,
DEFAULT_SIZE integer, DEFAULT_SIZE integer,
DEFAULT_FOLDERS Boolean, DEFAULT_IMPORT_FOLDERS Boolean,
DEFAULT_STORAGE_FOLDERS Boolean,
DEFAULT_FULLSCREEN Boolean, DEFAULT_FULLSCREEN Boolean,
constraint PK_PA_USER_ID primary key(ID) ); constraint PK_PA_USER_ID primary key(ID) );

View File

@@ -56,6 +56,10 @@
<div class="col col-auto my-auto"> <div class="col col-auto my-auto">
<span class="alert alert-primary p-2">Searched for: '{{search_term}}'</span> <span class="alert alert-primary p-2">Searched for: '{{search_term}}'</span>
</div class="col my-auto"> </div class="col my-auto">
<script>
$('#noo').prop('disabled', 'disabled').removeClass('border-info').addClass('border-secondary').removeClass('text-info').addClass('text-secondary');
$('#folders').prop('disabled', 'disabled').removeClass('border-info').addClass('border-secondary').removeClass('text-info').addClass('text-secondary');
</script>
{% endif %} {% endif %}
<div class="col flex-grow-1 my-auto d-flex justify-content-center w-100"> <div class="col flex-grow-1 my-auto d-flex justify-content-center w-100">
<button aria-label="prev" id="prev" name="prev" class="prev sm-txt btn btn-outline-secondary"> <button aria-label="prev" id="prev" name="prev" class="prev sm-txt btn btn-outline-secondary">

View File

@@ -6,44 +6,56 @@
<div class="row"> <div class="row">
<h3>Defaults for {{user.dn|Username}}</h3> <h3>Defaults for {{user.dn|Username}}</h3>
<div class="col-6"> <div class="col-7">
<div class="row"> <div class="row">
<div class="input-group"> <div class="input-group">
<label class="py-1 input-group-text col-6 justify-content-end">When viewing show in fullscreen:</label> <label class="py-1 input-group-text col-7 justify-content-end">Size of image thumbnails:</label>
{{CreateSelect( "size", user.default_size, ["XS", "S", "M", "L", "XL"], "ChangeDefault();return false", "col-2 rounded-end", { 0:64, 1:96, 2:128, 3:192, 4:256 } )|safe }} {{CreateSelect( "size", user.default_size, ["XS", "S", "M", "L", "XL"], "ChangeDefault();return false", "col-2 rounded-end", { 0:64, 1:96, 2:128, 3:192, 4:256 } )|safe }}
</div> </div>
</div class="row"> </div class="row">
<div class="row"> <div class="row">
<div class="input-group"> <div class="input-group">
<label class="py-1 input-group-text col-6 justify-content-end">Ordered by:</label> <label class="py-1 input-group-text col-7 justify-content-end"><b>Import</b>&nbsp; path ordered by:</label>
{{CreateSelect( "noo", user.default_noo, ["Oldest", "Newest","A to Z", "Z to A"], "ChangeDefault();return false", "col-2 rounded-end")|safe }} {{CreateSelect( "noo", user.default_import_noo, ["Oldest", "Newest","A to Z", "Z to A"], "ChangeDefault();return false", "col-2 rounded-end")|safe }}
</div class="input-group">
</div class="row">
<div class="row">
<div class="input-group">
<label class="py-1 input-group-text col-7 justify-content-end"><b>Storage</b>&nbsp; path ordered by:</label>
{{CreateSelect( "noo", user.default_storage_noo, ["Oldest", "Newest","A to Z", "Z to A"], "ChangeDefault();return false", "col-2 rounded-end")|safe }}
</div class="input-group"> </div class="input-group">
</div> </div>
<div class="row"> <div class="row">
<div class="input-group"> <div class="input-group">
<label class="py-1 input-group-text col-6 justify-content-end">How many thumbnails to show at once:</label> <label class="py-1 input-group-text col-7 justify-content-end">How many thumbnails to show at once:</label>
{{CreateSelect( "how_many", user.default_how_many, [10, 25, 50, 75, 100, 150, 200, 500], "ChangeDefault();return false", "col-2 rounded-end")|safe }} {{CreateSelect( "how_many", user.default_how_many, [10, 25, 50, 75, 100, 150, 200, 500], "ChangeDefault();return false", "col-2 rounded-end")|safe }}
</div class="input-group"> </div class="input-group">
</div> </div>
<div class="row"> <div class="row">
<div class="input-group"> <div class="input-group">
<label class="py-1 input-group-text col-6 justify-content-end">Group by:</label> <label class="py-1 input-group-text col-7 justify-content-end">Group by:</label>
{{CreateSelect( "grouping", user.default_grouping, ["None", "Day", "Week", "Month"], "ChangeDefault();return false", "col-2 rounded-end")|safe }} {{CreateSelect( "grouping", user.default_grouping, ["None", "Day", "Week", "Month"], "ChangeDefault();return false", "col-2 rounded-end")|safe }}
</div class="input-group"> </div class="input-group">
</div> </div>
<div class="row"> <div class="row">
<div class="input-group"> <div class="input-group">
<label class="py-1 input-group-text col-6 justify-content-end">Folders or Flat view of thumbnails:</label> <label class="py-1 input-group-text col-7 justify-content-end">Folders or Flat view of thumbnails in &nbsp;<b>import</b>&nbsp; path:</label>
{{CreateSelect( "folders", user.default_folders, ["In Folder", "Flat View"], "ChangeDefault();return false", "col-2 rounded-end", { 0:true, 1:false } )|safe }} {{CreateSelect( "folders", user.default_import_folders, ["In Folder", "Flat View"], "ChangeDefault();return false", "col-2 rounded-end", { 0:true, 1:false } )|safe }}
</div> </div>
</div> </div>
<div class="row"> <div class="row">
<div class="input-group"> <div class="input-group">
<label class="py-1 input-group-text col-6 justify-content-end">When viewing show in fullscreen:</label> <label class="py-1 input-group-text col-7 justify-content-end">Folders or Flat view of thumbnails in &nbsp;<b>storage</b>&nbsp; path:</label>
{{CreateSelect( "folders", user.default_storage_folders, ["In Folder", "Flat View"], "ChangeDefault();return false", "col-2 rounded-end", { 0:true, 1:false } )|safe }}
</div>
</div>
<div class="row">
<div class="input-group">
<label class="py-1 input-group-text col-7 justify-content-end">When viewing show in fullscreen:</label>
{{CreateSelect( "fullscreen", user.default_fullscreen, [True,False], "ChangeDefault();return false", "col-2 rounded-end")|safe }} {{CreateSelect( "fullscreen", user.default_fullscreen, [True,False], "ChangeDefault();return false", "col-2 rounded-end")|safe }}
</div> </div>
</div> </div>
</div class="col-6"> </div class="col-7">
<div class="row pt-5"> <div class="row pt-5">
<alert class="alert alert-warning">The following values are based on the defaults above and subsequent changes as you navigate the application and are not set by hand. The following content is for checking/debugging only.</alert> <alert class="alert alert-warning">The following values are based on the defaults above and subsequent changes as you navigate the application and are not set by hand. The following content is for checking/debugging only.</alert>

20
user.py
View File

@@ -20,11 +20,13 @@ class PAUser(UserMixin,db.Model):
__tablename__ = "pa_user" __tablename__ = "pa_user"
id = db.Column(db.Integer, db.Sequence('pa_user_id_seq'), primary_key=True) id = db.Column(db.Integer, db.Sequence('pa_user_id_seq'), primary_key=True)
dn = db.Column(db.String) dn = db.Column(db.String)
default_noo = db.Column(db.String) default_import_noo = db.Column(db.String)
default_storage_noo = db.Column(db.String)
default_grouping = db.Column(db.String) default_grouping = db.Column(db.String)
default_how_many = db.Column(db.Integer) default_how_many = db.Column(db.Integer)
default_size = db.Column(db.Integer) default_size = db.Column(db.Integer)
default_folders = db.Column(db.Boolean) default_import_folders = db.Column(db.Boolean)
default_storage_folders = db.Column(db.Boolean)
default_fullscreen = db.Column(db.Boolean) default_fullscreen = db.Column(db.Boolean)
def __repr__(self): def __repr__(self):
@@ -49,14 +51,18 @@ def changedefaults():
print( f"{el}={request.form[el]}" ) print( f"{el}={request.form[el]}" )
user=PAUser.query.filter(PAUser.dn==request.form['dn']).one() user=PAUser.query.filter(PAUser.dn==request.form['dn']).one()
user.default_size = request.form['default_size'] user.default_size = request.form['default_size']
user.default_noo = request.form['default_noo'] user.default_import_noo = request.form['default_import_noo']
user.default_storage_noo = request.form['default_storage_noo']
user.default_how_many = request.form['default_how_many'] user.default_how_many = request.form['default_how_many']
user.default_grouping = request.form['default_grouping'] user.default_grouping = request.form['default_grouping']
if request.form['default_folders'] == 'True': if request.form['default_import_folders'] == 'True':
user.default_folders = True user.default_import_folders = True
else: else:
user.default_folders = False user.default_import_folders = False
print("fullscreen is failing?") if request.form['default_storage_folders'] == 'True':
user.default_storage_folders = True
else:
user.default_storage_folders = False
if request.form['default_fullscreen'] == 'True': if request.form['default_fullscreen'] == 'True':
user.default_fullscreen = True user.default_fullscreen = True
else: else: