import sys import os import types import logging import stat import csv import re import datetime from PIL import Image from utils import save_carefully from functools import reduce import settings from troggle.core.models_survex import SingleScan, ScansFolder, TunnelFile from troggle.core.models import DataIssue def get_or_create_placeholder(year): """ All surveys must be related to a logbookentry. We don't have a way to automatically figure out which survey went with which logbookentry, so we create a survey placeholder logbook entry for each year. This function always returns such a placeholder, and creates it if it doesn't exist yet. """ lookupAttribs={'date__year':int(year), 'title':"placeholder for surveys",} nonLookupAttribs={'text':"surveys temporarily attached to this should be re-attached to their actual trips", 'date':datetime.date(int(year),1,1)} placeholder_logbook_entry, newly_created = save_carefully(LogbookEntry, lookupAttribs, nonLookupAttribs) return placeholder_logbook_entry def listdir(*directories): try: return os.listdir(os.path.join(settings.SURVEYS, *directories)) except: import urllib.request, urllib.parse, urllib.error url = settings.SURVEYS + reduce(lambda x, y: x + "/" + y, ["listdir"] + list(directories)) folders = urllib.request.urlopen(url.replace("#", "%23")).readlines() return [folder.rstrip(r"/") for folder in folders] # handles url or file, so we can refer to a set of scans on another server def GetListDir(sdir): res = [ ] if sdir[:7] == "http://": assert False, "Not written" s = urllib.request.urlopen(sdir) else: for f in os.listdir(sdir): if f[0] != ".": ff = os.path.join(sdir, f) res.append((f, ff, os.path.isdir(ff))) return res def LoadListScansFile(scansfolder): gld = [ ] # flatten out any directories in these wallet folders - should not be any for (fyf, ffyf, fisdiryf) in GetListDir(scansfolder.fpath): if fisdiryf: gld.extend(GetListDir(ffyf)) else: gld.append((fyf, ffyf, fisdiryf)) c=0 for (fyf, ffyf, fisdiryf) in gld: #assert not fisdiryf, ffyf if re.search(r"\.(?:png|jpg|jpeg|pdf|svg|gif)(?i)$", fyf): singlescan = SingleScan(ffile=ffyf, name=fyf, scansfolder=scansfolder) singlescan.save() c+=1 if c>=10: print(".", end='') c = 0 # this iterates through the scans directories (either here or on the remote server) # and builds up the models we can access later def LoadListScans(): print(' - Loading Survey Scans') SingleScan.objects.all().delete() ScansFolder.objects.all().delete() print(' - deleting all scansFolder and scansSingle objects') # first do the smkhs (large kh survey scans) directory manyscansfoldersmkhs = ScansFolder(fpath=os.path.join(settings.SURVEY_SCANS, "../surveys/smkhs"), walletname="smkhs") print("smkhs", end=' ') if os.path.isdir(manyscansfoldersmkhs.fpath): manyscansfoldersmkhs.save() LoadListScansFile(manyscansfoldersmkhs) # iterate into the surveyscans directory print(' - ', end=' ') for f, ff, fisdir in GetListDir(settings.SURVEY_SCANS): if not fisdir: continue # do the year folders if re.match(r"\d\d\d\d$", f): print("%s" % f, end=' ') for fy, ffy, fisdiry in GetListDir(ff): if fisdiry: assert fisdiry, ffy scansfolder = ScansFolder(fpath=ffy, walletname=fy) scansfolder.save() LoadListScansFile(scansfolder) # do the elif f != "thumbs": scansfolder = ScansFolder(fpath=ff, walletname=f) scansfolder.save() LoadListScansFile(scansfolder) def FindTunnelScan(tunnelfile, path): scansfolder, scansfile = None, None mscansdir = re.search(rb"(\d\d\d\d#X?\d+\w?|1995-96kh|92-94Surveybookkh|1991surveybook|smkhs)/(.*?(?:png|jpg|pdf|jpeg))$", path) if mscansdir: scansfolderl = ScansFolder.objects.filter(walletname=mscansdir.group(1)) if len(scansfolderl): assert len(scansfolderl) == 1 scansfolder = scansfolderl[0] if scansfolder: scansfilel = scansfolder.singlescan_set.filter(name=mscansdir.group(2)) if len(scansfilel): if len(scansfilel) > 1: message = "! More than one image filename matches filter query. [{}]: {} {} {} {}".format(scansfilel[0], mscansdir.group(1), mscansdir.group(2), tunnelfile.tunnelpath, path) print(message) DataIssue.objects.create(parser='Drawings', message=message) scansfile = scansfilel[0] if scansfolder: tunnelfile.manyscansfolders.add(scansfolder) if scansfile: tunnelfile.scans.add(scansfile) elif path and not re.search(rb"\.(?:png|jpg|pdf|jpeg|gif|pdf)$(?i)", path): name = os.path.split(path)[1] rtunnelfilel = TunnelFile.objects.filter(tunnelname=name) if len(rtunnelfilel): message = "! Two paths with same name [{}]: {}".format(path, name) print(message) DataIssue.objects.create(parser='Drawings', message=message) rtunnelfile = rtunnelfilel[0] tunnelfile.tunnelcontains.add(rtunnelfile) tunnelfile.save() def SetTunnelfileInfo(tunnelfile): ff = os.path.join(settings.TUNNEL_DATA, tunnelfile.tunnelpath) tunnelfile.filesize = os.stat(ff)[stat.ST_SIZE] if tunnelfile.filesize <= 0: message = "! Zero length xml file {}".format(ff) print(message) DataIssue.objects.create(parser='Drawings', message=message) return fin = open(ff,'rb') ttext = fin.read() fin.close() mtype = re.search(rb"<(fontcolours|sketch)", ttext) tunnelfile.bfontcolours = (mtype.group(1)=="fontcolours") tunnelfile.npaths = len(re.findall(rb" # for path, style in re.findall(rb'