mirror of
https://github.com/GAM-team/GAM.git
synced 2026-06-27 01:11:37 +00:00
Remove deprecated CloudPrint commands
This commit is contained in:
@@ -1,486 +0,0 @@
|
||||
{
|
||||
"kind": "discovery#restDescription",
|
||||
"discoveryVersion": "v1",
|
||||
"id": "cloudprint:v2",
|
||||
"name": "cloudprint",
|
||||
"version": "v2",
|
||||
"revision": "20150605",
|
||||
"title": "Cloud Print API",
|
||||
"description": "Lets you access Cloud Print Printers",
|
||||
"ownerDomain": "google.com",
|
||||
"ownerName": "Google",
|
||||
"icons": {
|
||||
"x16": "http://www.google.com/images/icons/product/search-16.gif",
|
||||
"x32": "http://www.google.com/images/icons/product/search-32.gif"
|
||||
},
|
||||
"documentationLink": "https://developers.google.com/cloud-print",
|
||||
"protocol": "rest",
|
||||
"baseUrl": "https://www.google.com/",
|
||||
"basePath": "/cloudprint/",
|
||||
"rootUrl": "https://www.google.com/",
|
||||
"servicePath": "/cloudprint/",
|
||||
"parameters": {
|
||||
"prettyPrint": {
|
||||
"type": "boolean",
|
||||
"description": "Returns response with indentations and line breaks.",
|
||||
"default": "true",
|
||||
"location": "query"
|
||||
}
|
||||
},
|
||||
"auth": {
|
||||
"oauth2": {
|
||||
"scopes": {
|
||||
"https://www.googleapis.com/auth/cloudprint": {
|
||||
"description": "Manage Cloud Print"
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
"schemas": {
|
||||
"Job": {
|
||||
"id": "Job",
|
||||
"type": "object",
|
||||
"description": "Job Object",
|
||||
"properties": {
|
||||
"title": {
|
||||
"type": "string",
|
||||
"description": "Job Title"
|
||||
},
|
||||
"id": {
|
||||
"type": "string",
|
||||
"description": "Unique ID"
|
||||
}
|
||||
}
|
||||
},
|
||||
"Jobs": {
|
||||
"id": "Jobs",
|
||||
"type": "object",
|
||||
"description": "List of Jobs.",
|
||||
"properties": {
|
||||
"jobs": {
|
||||
"type": "array",
|
||||
"description": "List of job objects.",
|
||||
"items": {
|
||||
"$ref": "Job"
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
"Printer": {
|
||||
"id": "Printer",
|
||||
"type": "object",
|
||||
"description": "Printer Object",
|
||||
"properties": {
|
||||
"displayName": {
|
||||
"type": "string",
|
||||
"description": "Display Name"
|
||||
},
|
||||
"id": {
|
||||
"type": "string",
|
||||
"description": "Unique ID"
|
||||
}
|
||||
}
|
||||
},
|
||||
"Printers": {
|
||||
"id": "Printers",
|
||||
"type": "object",
|
||||
"description": "List of Printers.",
|
||||
"properties": {
|
||||
"printers": {
|
||||
"type": "array",
|
||||
"description": "List of printer objects.",
|
||||
"items": {
|
||||
"$ref": "Printer"
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
"resources": {
|
||||
"jobs": {
|
||||
"methods": {
|
||||
"delete": {
|
||||
"id": "cloudprint.jobs.delete",
|
||||
"path": "deletejob",
|
||||
"httpMethod": "GET",
|
||||
"parameters": {
|
||||
"jobid": {
|
||||
"type": "string",
|
||||
"location": "query",
|
||||
"required": "true"
|
||||
}
|
||||
}
|
||||
},
|
||||
"fetch": {
|
||||
"id": "cloudprint.jobs.fetch",
|
||||
"path": "fetch",
|
||||
"httpMethod": "GET",
|
||||
"parameters": {
|
||||
"printerid": {
|
||||
"type": "string",
|
||||
"required": "true",
|
||||
"location": "query"
|
||||
}
|
||||
},
|
||||
"response": {
|
||||
"$ref": "Jobs"
|
||||
}
|
||||
},
|
||||
"getticket": {
|
||||
"id": "cloudprint.jobs.getticket",
|
||||
"path": "ticket",
|
||||
"httpMethod": "GET",
|
||||
"parameters": {
|
||||
"jobid": {
|
||||
"type": "string",
|
||||
"required": "true",
|
||||
"location": "query"
|
||||
},
|
||||
"use_cjt": {
|
||||
"type": "boolean",
|
||||
"required": "true",
|
||||
"location": "query"
|
||||
}
|
||||
}
|
||||
},
|
||||
"list": {
|
||||
"id": "cloudprint.jobs.list",
|
||||
"path": "jobs",
|
||||
"httpMethod": "GET",
|
||||
"parameters": {
|
||||
"printerid": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
},
|
||||
"owner": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
},
|
||||
"status": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
},
|
||||
"q": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
},
|
||||
"offset": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
},
|
||||
"limit": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
},
|
||||
"sortorder": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
}
|
||||
},
|
||||
"response": {
|
||||
"$ref": "Jobs"
|
||||
}
|
||||
},
|
||||
"update": {
|
||||
"id": "cloudprint.jobs.update",
|
||||
"path": "control",
|
||||
"httpMethod": "GET",
|
||||
"parameters": {
|
||||
"jobid": {
|
||||
"type": "string",
|
||||
"required": "true",
|
||||
"location": "query"
|
||||
},
|
||||
"semantic_state_diff": {
|
||||
"type": "string",
|
||||
"required": "true",
|
||||
"location": "query"
|
||||
}
|
||||
},
|
||||
"response": {
|
||||
"$ref": "Jobs"
|
||||
}
|
||||
},
|
||||
"resubmit": {
|
||||
"id": "cloudprint.jobs.resubmit",
|
||||
"path": "resubmit",
|
||||
"httpMethod": "POST",
|
||||
"description": "resubmit a job to new printer.",
|
||||
"parameters": {
|
||||
"printerid": {
|
||||
"type": "string",
|
||||
"required": "true",
|
||||
"location": "query"
|
||||
},
|
||||
"jobid": {
|
||||
"type": "string",
|
||||
"required": "true",
|
||||
"location": "query"
|
||||
},
|
||||
"ticket": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
}
|
||||
},
|
||||
"response": {
|
||||
"$ref": "Job"
|
||||
}
|
||||
},
|
||||
"submit": {
|
||||
"id": "cloudprint.jobs.submit",
|
||||
"path": "submit",
|
||||
"httpMethod": "POST",
|
||||
"description": "Send a print job to cloud print.",
|
||||
"request": {
|
||||
"printerid": {
|
||||
"type": "string",
|
||||
"required": "true",
|
||||
"location": "query"
|
||||
},
|
||||
"title": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
},
|
||||
"ticket": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
},
|
||||
"content": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
},
|
||||
"contentType": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
},
|
||||
"tag": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
}
|
||||
},
|
||||
"response": {
|
||||
"$ref": "Job"
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
"printers": {
|
||||
"methods": {
|
||||
"get": {
|
||||
"id": "cloudprint.printers.get",
|
||||
"path": "printer",
|
||||
"httpMethod": "GET",
|
||||
"parameters": {
|
||||
"printerid": {
|
||||
"type": "string",
|
||||
"required": "true",
|
||||
"location": "query"
|
||||
},
|
||||
"extra_fields": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
}
|
||||
},
|
||||
"response": {
|
||||
"$ref": "Printer"
|
||||
}
|
||||
},
|
||||
"list": {
|
||||
"id": "cloudprint.printers.list",
|
||||
"path": "search",
|
||||
"httpMethod": "GET",
|
||||
"description": "List all printers",
|
||||
"parameters": {
|
||||
"q": {
|
||||
"type": "string",
|
||||
"description": "Query list of printers",
|
||||
"location": "query"
|
||||
},
|
||||
"type": {
|
||||
"type": "string",
|
||||
"description": "limit results to printers of type",
|
||||
"location": "query"
|
||||
},
|
||||
"connection_status": {
|
||||
"type": "string",
|
||||
"description": "limit results to printers with this status",
|
||||
"location": "query"
|
||||
},
|
||||
"extra_fields": {
|
||||
"type": "string",
|
||||
"description": "include extra fields",
|
||||
"location": "query"
|
||||
}
|
||||
},
|
||||
"response": {
|
||||
"$ref": "Printers"
|
||||
}
|
||||
},
|
||||
"share": {
|
||||
"id": "cloudprint.printers.share",
|
||||
"path": "share",
|
||||
"httpMethod": "GET",
|
||||
"description": "Share printer with user, group or domain",
|
||||
"parameters": {
|
||||
"printerid": {
|
||||
"type": "string",
|
||||
"required": "true",
|
||||
"location": "query"
|
||||
},
|
||||
"scope": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
},
|
||||
"role": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
},
|
||||
"type": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
},
|
||||
"skip_notification": {
|
||||
"type": "boolean",
|
||||
"location": "query"
|
||||
},
|
||||
"public": {
|
||||
"type": "boolean",
|
||||
"location": "query"
|
||||
}
|
||||
}
|
||||
},
|
||||
"unshare": {
|
||||
"id": "cloudprint.printers.unshare",
|
||||
"path": "unshare",
|
||||
"httpMethod": "GET",
|
||||
"description": "unshare printer with user, group or domain",
|
||||
"parameters": {
|
||||
"printerid": {
|
||||
"type": "string",
|
||||
"required": "true",
|
||||
"location": "query"
|
||||
},
|
||||
"scope": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
},
|
||||
"public": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
}
|
||||
}
|
||||
},
|
||||
"delete": {
|
||||
"id": "cloudprint.printers.delete",
|
||||
"path": "delete",
|
||||
"httpMethod": "GET",
|
||||
"description": "delete a printer",
|
||||
"parameters": {
|
||||
"printerid": {
|
||||
"type": "string",
|
||||
"required": "true",
|
||||
"location": "query"
|
||||
}
|
||||
}
|
||||
},
|
||||
"update": {
|
||||
"id": "cloudprint.printers.update",
|
||||
"path": "update",
|
||||
"httpMethod": "GET",
|
||||
"description": "update a printer",
|
||||
"parameters": {
|
||||
"isTosAccepted": {
|
||||
"type": "boolean",
|
||||
"location": "query"
|
||||
},
|
||||
"gcpVersion": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
},
|
||||
"setupUrl": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
},
|
||||
"supportUrl": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
},
|
||||
"firmware": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
},
|
||||
"currentQuota": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
},
|
||||
"type": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
},
|
||||
"public": {
|
||||
"type": "boolean",
|
||||
"location": "query"
|
||||
},
|
||||
"status": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
},
|
||||
"proxy": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
},
|
||||
"manufacturer": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
},
|
||||
"defaultDisplayName": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
},
|
||||
"displayName": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
},
|
||||
"name": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
},
|
||||
"uuid": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
},
|
||||
"updateUrl": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
},
|
||||
"ownerId": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
},
|
||||
"model": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
},
|
||||
"description": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
},
|
||||
"printerid": {
|
||||
"type": "string",
|
||||
"required": "true",
|
||||
"location": "query"
|
||||
},
|
||||
"quotaEnabled": {
|
||||
"type": "boolean",
|
||||
"location": "query"
|
||||
},
|
||||
"dailyQuota": {
|
||||
"type": "string",
|
||||
"location": "query"
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -7,11 +7,9 @@ from PyInstaller.utils.hooks import copy_metadata
|
||||
|
||||
sys.modules['FixTk'] = None
|
||||
|
||||
extra_files = [('cloudprint-v2.json', 'cloudprint-v2.json')]
|
||||
|
||||
# dynamically determine where httplib2/cacerts.txt lives
|
||||
proot = os.path.dirname(importlib.import_module('httplib2').__file__)
|
||||
extra_files += [(os.path.join(proot, 'cacerts.txt'), 'httplib2')]
|
||||
extra_files = [(os.path.join(proot, 'cacerts.txt'), 'httplib2')]
|
||||
|
||||
extra_files += copy_metadata('google-api-python-client')
|
||||
|
||||
|
||||
@@ -2783,695 +2783,6 @@ def doPrintCourseParticipants():
|
||||
display.write_csv_file(csvRows, titles, 'Course Participants', todrive)
|
||||
|
||||
|
||||
def doPrintPrintJobs():
|
||||
cp = buildGAPIObject('cloudprint')
|
||||
todrive = False
|
||||
titles = ['printerid', 'id']
|
||||
csvRows = []
|
||||
printerid = None
|
||||
owner = None
|
||||
status = None
|
||||
sortorder = None
|
||||
descending = False
|
||||
query = None
|
||||
age = None
|
||||
older_or_newer = None
|
||||
jobLimit = PRINTJOBS_DEFAULT_JOB_LIMIT
|
||||
i = 3
|
||||
while i < len(sys.argv):
|
||||
myarg = sys.argv[i].lower().replace('_', '')
|
||||
if myarg == 'todrive':
|
||||
todrive = True
|
||||
i += 1
|
||||
elif myarg in ['olderthan', 'newerthan']:
|
||||
if myarg == 'olderthan':
|
||||
older_or_newer = 'older'
|
||||
else:
|
||||
older_or_newer = 'newer'
|
||||
age_number = sys.argv[i + 1][:-1]
|
||||
if not age_number.isdigit():
|
||||
controlflow.system_error_exit(
|
||||
2, f'expected a number; got {age_number}')
|
||||
age_unit = sys.argv[i + 1][-1].lower()
|
||||
if age_unit == 'm':
|
||||
age = int(time.time()) - (int(age_number) * 60)
|
||||
elif age_unit == 'h':
|
||||
age = int(time.time()) - (int(age_number) * 60 * 60)
|
||||
elif age_unit == 'd':
|
||||
age = int(time.time()) - (int(age_number) * 60 * 60 * 24)
|
||||
else:
|
||||
controlflow.system_error_exit(
|
||||
2,
|
||||
f'expected m (minutes), h (hours) or d (days); got {age_unit}'
|
||||
)
|
||||
i += 2
|
||||
elif myarg == 'query':
|
||||
query = sys.argv[i + 1]
|
||||
i += 2
|
||||
elif myarg == 'status':
|
||||
status = sys.argv[i + 1]
|
||||
i += 2
|
||||
elif myarg == 'ascending':
|
||||
descending = False
|
||||
i += 1
|
||||
elif myarg == 'descending':
|
||||
descending = True
|
||||
i += 1
|
||||
elif myarg == 'orderby':
|
||||
sortorder = sys.argv[i + 1].lower().replace('_', '')
|
||||
if sortorder not in PRINTJOB_ASCENDINGORDER_MAP:
|
||||
controlflow.expected_argument_exit(
|
||||
'orderby', ', '.join(PRINTJOB_ASCENDINGORDER_MAP),
|
||||
sortorder)
|
||||
sortorder = PRINTJOB_ASCENDINGORDER_MAP[sortorder]
|
||||
i += 2
|
||||
elif myarg in ['printer', 'printerid']:
|
||||
printerid = sys.argv[i + 1]
|
||||
i += 2
|
||||
elif myarg in ['owner', 'user']:
|
||||
owner = sys.argv[i + 1]
|
||||
i += 2
|
||||
elif myarg == 'limit':
|
||||
jobLimit = getInteger(sys.argv[i + 1], myarg, minVal=0)
|
||||
i += 2
|
||||
else:
|
||||
controlflow.invalid_argument_exit(sys.argv[i],
|
||||
'gam print printjobs')
|
||||
if sortorder and descending:
|
||||
sortorder = PRINTJOB_DESCENDINGORDER_MAP[sortorder]
|
||||
if printerid:
|
||||
result = gapi.call(cp.printers(), 'get', printerid=printerid)
|
||||
checkCloudPrintResult(result)
|
||||
if ((not sortorder) or
|
||||
(sortorder == 'CREATE_TIME_DESC')) and (older_or_newer == 'newer'):
|
||||
timeExit = True
|
||||
elif (sortorder == 'CREATE_TIME') and (older_or_newer == 'older'):
|
||||
timeExit = True
|
||||
else:
|
||||
timeExit = False
|
||||
jobCount = offset = 0
|
||||
while True:
|
||||
if jobLimit == 0:
|
||||
limit = PRINTJOBS_DEFAULT_MAX_RESULTS
|
||||
else:
|
||||
limit = min(PRINTJOBS_DEFAULT_MAX_RESULTS, jobLimit - jobCount)
|
||||
if limit == 0:
|
||||
break
|
||||
result = gapi.call(cp.jobs(),
|
||||
'list',
|
||||
printerid=printerid,
|
||||
q=query,
|
||||
status=status,
|
||||
sortorder=sortorder,
|
||||
owner=owner,
|
||||
offset=offset,
|
||||
limit=limit)
|
||||
checkCloudPrintResult(result)
|
||||
newJobs = result['range']['jobsCount']
|
||||
totalJobs = int(result['range']['jobsTotal'])
|
||||
if GC_Values[GC_DEBUG_LEVEL] > 0:
|
||||
sys.stderr.write(
|
||||
f'Debug: jobCount: {jobCount}, jobLimit: {jobLimit}, jobsCount: {newJobs}, jobsTotal: {totalJobs}\n'
|
||||
)
|
||||
if newJobs == 0:
|
||||
break
|
||||
jobCount += newJobs
|
||||
offset += newJobs
|
||||
for job in result['jobs']:
|
||||
createTime = int(job['createTime']) / 1000
|
||||
if older_or_newer:
|
||||
if older_or_newer == 'older' and createTime > age:
|
||||
if timeExit:
|
||||
jobCount = totalJobs
|
||||
break
|
||||
continue
|
||||
if older_or_newer == 'newer' and createTime < age:
|
||||
if timeExit:
|
||||
jobCount = totalJobs
|
||||
break
|
||||
continue
|
||||
job['createTime'] = utils.formatTimestampYMDHMS(job['createTime'])
|
||||
job['updateTime'] = utils.formatTimestampYMDHMS(job['updateTime'])
|
||||
job['tags'] = ' '.join(job['tags'])
|
||||
display.add_row_titles_to_csv_file(utils.flatten_json(job), csvRows,
|
||||
titles)
|
||||
if jobCount >= totalJobs:
|
||||
break
|
||||
display.write_csv_file(csvRows, titles, 'Print Jobs', todrive)
|
||||
|
||||
|
||||
def doPrintPrinters():
|
||||
cp = buildGAPIObject('cloudprint')
|
||||
todrive = False
|
||||
titles = [
|
||||
'id',
|
||||
]
|
||||
csvRows = []
|
||||
queries = [None]
|
||||
printer_type = None
|
||||
connection_status = None
|
||||
extra_fields = None
|
||||
i = 3
|
||||
while i < len(sys.argv):
|
||||
myarg = sys.argv[i].lower().replace('_', '')
|
||||
if myarg in ['query', 'queries']:
|
||||
queries = getQueries(myarg, sys.argv[i + 1])
|
||||
i += 2
|
||||
elif myarg == 'type':
|
||||
printer_type = sys.argv[i + 1]
|
||||
i += 2
|
||||
elif myarg == 'status':
|
||||
connection_status = sys.argv[i + 1]
|
||||
i += 2
|
||||
elif myarg == 'extrafields':
|
||||
extra_fields = sys.argv[i + 1]
|
||||
i += 2
|
||||
elif myarg == 'todrive':
|
||||
todrive = True
|
||||
i += 1
|
||||
else:
|
||||
controlflow.invalid_argument_exit(sys.argv[i], 'gam print printers')
|
||||
for query in queries:
|
||||
printers = gapi.call(cp.printers(),
|
||||
'list',
|
||||
q=query,
|
||||
type=printer_type,
|
||||
connection_status=connection_status,
|
||||
extra_fields=extra_fields)
|
||||
checkCloudPrintResult(printers)
|
||||
for printer in printers['printers']:
|
||||
printer['createTime'] = utils.formatTimestampYMDHMS(
|
||||
printer['createTime'])
|
||||
printer['accessTime'] = utils.formatTimestampYMDHMS(
|
||||
printer['accessTime'])
|
||||
printer['updateTime'] = utils.formatTimestampYMDHMS(
|
||||
printer['updateTime'])
|
||||
printer['tags'] = ' '.join(printer['tags'])
|
||||
display.add_row_titles_to_csv_file(utils.flatten_json(printer),
|
||||
csvRows, titles)
|
||||
display.write_csv_file(csvRows, titles, 'Printers', todrive)
|
||||
|
||||
|
||||
def doPrinterShowACL():
|
||||
cp = buildGAPIObject('cloudprint')
|
||||
show_printer = sys.argv[2]
|
||||
printer_info = gapi.call(cp.printers(), 'get', printerid=show_printer)
|
||||
checkCloudPrintResult(printer_info)
|
||||
for acl in printer_info['printers'][0]['access']:
|
||||
if 'key' in acl:
|
||||
acl['accessURL'] = f'https://www.google.com/cloudprint/addpublicprinter.html?printerid={show_printer}&key={acl["key"]}'
|
||||
display.print_json(acl)
|
||||
print()
|
||||
|
||||
|
||||
def doPrinterAddACL():
|
||||
cp = buildGAPIObject('cloudprint')
|
||||
printer = sys.argv[2]
|
||||
role = sys.argv[4].upper()
|
||||
scope = sys.argv[5]
|
||||
notify = bool(len(sys.argv) > 6 and sys.argv[6].lower() == 'notify')
|
||||
public = None
|
||||
skip_notification = True
|
||||
if scope.lower() == 'public':
|
||||
public = True
|
||||
scope = None
|
||||
role = None
|
||||
skip_notification = None
|
||||
elif scope.find('@') == -1:
|
||||
scope = f'/hd/domain/{scope}'
|
||||
else:
|
||||
skip_notification = not notify
|
||||
result = gapi.call(cp.printers(),
|
||||
'share',
|
||||
printerid=printer,
|
||||
role=role,
|
||||
scope=scope,
|
||||
public=public,
|
||||
skip_notification=skip_notification)
|
||||
checkCloudPrintResult(result)
|
||||
who = scope
|
||||
if who is None:
|
||||
who = 'public'
|
||||
role = 'user'
|
||||
print(f'Added {role} {who}')
|
||||
|
||||
|
||||
def doPrinterDelACL():
|
||||
cp = buildGAPIObject('cloudprint')
|
||||
printer = sys.argv[2]
|
||||
scope = sys.argv[4]
|
||||
public = None
|
||||
if scope.lower() == 'public':
|
||||
public = True
|
||||
scope = None
|
||||
elif scope.find('@') == -1:
|
||||
scope = f'/hd/domain/{scope}'
|
||||
result = gapi.call(cp.printers(),
|
||||
'unshare',
|
||||
printerid=printer,
|
||||
scope=scope,
|
||||
public=public)
|
||||
checkCloudPrintResult(result)
|
||||
who = scope
|
||||
if who is None:
|
||||
who = 'public'
|
||||
print(f'Removed {who}')
|
||||
|
||||
|
||||
def encode_multipart(fields, files, boundary=None):
|
||||
|
||||
def escape_quote(s):
|
||||
return s.replace('"', '\\"')
|
||||
|
||||
def getFormDataLine(name, value, boundary):
|
||||
return f'--{boundary}', f'Content-Disposition: form-data; name="{escape_quote(name)}"', '', str(
|
||||
value)
|
||||
|
||||
if boundary is None:
|
||||
boundary = ''.join(random.choice(ALPHANUMERIC_CHARS) for _ in range(30))
|
||||
lines = []
|
||||
for name, value in list(fields.items()):
|
||||
if name == 'tags':
|
||||
for tag in value:
|
||||
lines.extend(getFormDataLine('tag', tag, boundary))
|
||||
else:
|
||||
lines.extend(getFormDataLine(name, value, boundary))
|
||||
for name, value in list(files.items()):
|
||||
filename = value['filename']
|
||||
mimetype = value['mimetype']
|
||||
lines.extend((
|
||||
f'--{boundary}',
|
||||
f'Content-Disposition: form-data; name="{escape_quote(name)}"; filename="{escape_quote(filename)}"',
|
||||
f'Content-Type: {mimetype}',
|
||||
'',
|
||||
value['content'],
|
||||
))
|
||||
lines.extend((
|
||||
f'--{boundary}--',
|
||||
'',
|
||||
))
|
||||
body = '\r\n'.join(lines)
|
||||
headers = {
|
||||
'Content-Type': f'multipart/form-data; boundary={boundary}',
|
||||
'Content-Length': str(len(body)),
|
||||
}
|
||||
return (body, headers)
|
||||
|
||||
|
||||
def doPrintJobFetch():
|
||||
cp = buildGAPIObject('cloudprint')
|
||||
printerid = sys.argv[2]
|
||||
if printerid == 'any':
|
||||
printerid = None
|
||||
owner = None
|
||||
status = None
|
||||
sortorder = None
|
||||
descending = False
|
||||
query = None
|
||||
age = None
|
||||
older_or_newer = None
|
||||
jobLimit = PRINTJOBS_DEFAULT_JOB_LIMIT
|
||||
targetFolder = os.getcwd()
|
||||
i = 4
|
||||
while i < len(sys.argv):
|
||||
myarg = sys.argv[i].lower().replace('_', '')
|
||||
if myarg in ['olderthan', 'newerthan']:
|
||||
if myarg == 'olderthan':
|
||||
older_or_newer = 'older'
|
||||
else:
|
||||
older_or_newer = 'newer'
|
||||
age_number = sys.argv[i + 1][:-1]
|
||||
if not age_number.isdigit():
|
||||
controlflow.system_error_exit(
|
||||
2, f'expected a number; got {age_number}')
|
||||
age_unit = sys.argv[i + 1][-1].lower()
|
||||
if age_unit == 'm':
|
||||
age = int(time.time()) - (int(age_number) * 60)
|
||||
elif age_unit == 'h':
|
||||
age = int(time.time()) - (int(age_number) * 60 * 60)
|
||||
elif age_unit == 'd':
|
||||
age = int(time.time()) - (int(age_number) * 60 * 60 * 24)
|
||||
else:
|
||||
controlflow.system_error_exit(
|
||||
2,
|
||||
f'expected m (minutes), h (hours) or d (days); got {age_unit}'
|
||||
)
|
||||
i += 2
|
||||
elif myarg == 'query':
|
||||
query = sys.argv[i + 1]
|
||||
i += 2
|
||||
elif myarg == 'status':
|
||||
status = sys.argv[i + 1]
|
||||
i += 2
|
||||
elif myarg == 'ascending':
|
||||
descending = False
|
||||
i += 1
|
||||
elif myarg == 'descending':
|
||||
descending = True
|
||||
i += 1
|
||||
elif myarg == 'orderby':
|
||||
sortorder = sys.argv[i + 1].lower().replace('_', '')
|
||||
if sortorder not in PRINTJOB_ASCENDINGORDER_MAP:
|
||||
controlflow.expected_argument_exit(
|
||||
'orderby', ', '.join(PRINTJOB_ASCENDINGORDER_MAP),
|
||||
sortorder)
|
||||
sortorder = PRINTJOB_ASCENDINGORDER_MAP[sortorder]
|
||||
i += 2
|
||||
elif myarg in ['owner', 'user']:
|
||||
owner = sys.argv[i + 1]
|
||||
i += 2
|
||||
elif myarg == 'limit':
|
||||
jobLimit = getInteger(sys.argv[i + 1], myarg, minVal=0)
|
||||
i += 2
|
||||
elif myarg == 'drivedir':
|
||||
targetFolder = GC_Values[GC_DRIVE_DIR]
|
||||
i += 1
|
||||
elif myarg == 'targetfolder':
|
||||
targetFolder = os.path.expanduser(sys.argv[i + 1])
|
||||
if not os.path.isdir(targetFolder):
|
||||
os.makedirs(targetFolder)
|
||||
i += 2
|
||||
else:
|
||||
controlflow.invalid_argument_exit(sys.argv[i],
|
||||
'gam printjobs fetch')
|
||||
if sortorder and descending:
|
||||
sortorder = PRINTJOB_DESCENDINGORDER_MAP[sortorder]
|
||||
if printerid:
|
||||
result = gapi.call(cp.printers(), 'get', printerid=printerid)
|
||||
checkCloudPrintResult(result)
|
||||
ssd = '{"state": {"type": "DONE"}}'
|
||||
if ((not sortorder) or
|
||||
(sortorder == 'CREATE_TIME_DESC')) and (older_or_newer == 'newer'):
|
||||
timeExit = True
|
||||
elif (sortorder == 'CREATE_TIME') and (older_or_newer == 'older'):
|
||||
timeExit = True
|
||||
else:
|
||||
timeExit = False
|
||||
jobCount = offset = 0
|
||||
while True:
|
||||
if jobLimit == 0:
|
||||
limit = PRINTJOBS_DEFAULT_MAX_RESULTS
|
||||
else:
|
||||
limit = min(PRINTJOBS_DEFAULT_MAX_RESULTS, jobLimit - jobCount)
|
||||
if limit == 0:
|
||||
break
|
||||
result = gapi.call(cp.jobs(),
|
||||
'list',
|
||||
printerid=printerid,
|
||||
q=query,
|
||||
status=status,
|
||||
sortorder=sortorder,
|
||||
owner=owner,
|
||||
offset=offset,
|
||||
limit=limit)
|
||||
checkCloudPrintResult(result)
|
||||
newJobs = result['range']['jobsCount']
|
||||
totalJobs = int(result['range']['jobsTotal'])
|
||||
if newJobs == 0:
|
||||
break
|
||||
jobCount += newJobs
|
||||
offset += newJobs
|
||||
for job in result['jobs']:
|
||||
createTime = int(job['createTime']) / 1000
|
||||
if older_or_newer:
|
||||
if older_or_newer == 'older' and createTime > age:
|
||||
if timeExit:
|
||||
jobCount = totalJobs
|
||||
break
|
||||
continue
|
||||
if older_or_newer == 'newer' and createTime < age:
|
||||
if timeExit:
|
||||
jobCount = totalJobs
|
||||
break
|
||||
continue
|
||||
fileUrl = job['fileUrl']
|
||||
jobid = job['id']
|
||||
fileName = os.path.join(
|
||||
targetFolder,
|
||||
f'{"".join(c if c in FILENAME_SAFE_CHARS else "_" for c in job["title"])}-{jobid}'
|
||||
)
|
||||
_, content = cp._http.request(uri=fileUrl, method='GET')
|
||||
if fileutils.write_file(fileName,
|
||||
content,
|
||||
mode='wb',
|
||||
continue_on_error=True):
|
||||
# ticket = gapi.call(cp.jobs(), u'getticket', jobid=jobid, use_cjt=True)
|
||||
result = gapi.call(cp.jobs(),
|
||||
'update',
|
||||
jobid=jobid,
|
||||
semantic_state_diff=ssd)
|
||||
checkCloudPrintResult(result)
|
||||
print(f'Printed job {jobid} to {fileName}')
|
||||
if jobCount >= totalJobs:
|
||||
break
|
||||
if jobCount == 0:
|
||||
print('No print jobs.')
|
||||
|
||||
|
||||
def doDelPrinter():
|
||||
cp = buildGAPIObject('cloudprint')
|
||||
printerid = sys.argv[3]
|
||||
result = gapi.call(cp.printers(), 'delete', printerid=printerid)
|
||||
checkCloudPrintResult(result)
|
||||
|
||||
|
||||
def doGetPrinterInfo():
|
||||
cp = buildGAPIObject('cloudprint')
|
||||
printerid = sys.argv[3]
|
||||
everything = False
|
||||
i = 4
|
||||
while i < len(sys.argv):
|
||||
myarg = sys.argv[i].lower()
|
||||
if myarg == 'everything':
|
||||
everything = True
|
||||
i += 1
|
||||
else:
|
||||
controlflow.invalid_argument_exit(sys.argv[i], 'gam info printer')
|
||||
result = gapi.call(cp.printers(), 'get', printerid=printerid)
|
||||
checkCloudPrintResult(result)
|
||||
printer_info = result['printers'][0]
|
||||
printer_info['createTime'] = utils.formatTimestampYMDHMS(
|
||||
printer_info['createTime'])
|
||||
printer_info['accessTime'] = utils.formatTimestampYMDHMS(
|
||||
printer_info['accessTime'])
|
||||
printer_info['updateTime'] = utils.formatTimestampYMDHMS(
|
||||
printer_info['updateTime'])
|
||||
printer_info['tags'] = ' '.join(printer_info['tags'])
|
||||
if not everything:
|
||||
del printer_info['capabilities']
|
||||
del printer_info['access']
|
||||
display.print_json(printer_info)
|
||||
|
||||
|
||||
def doUpdatePrinter():
|
||||
cp = buildGAPIObject('cloudprint')
|
||||
printerid = sys.argv[3]
|
||||
kwargs = {}
|
||||
i = 4
|
||||
update_items = [
|
||||
'isTosAccepted', 'gcpVersion', 'setupUrl', 'quotaEnabled', 'id',
|
||||
'supportUrl', 'firmware', 'currentQuota', 'type', 'public', 'status',
|
||||
'description', 'defaultDisplayName', 'proxy', 'dailyQuota',
|
||||
'manufacturer', 'displayName', 'name', 'uuid', 'updateUrl', 'ownerId',
|
||||
'model'
|
||||
]
|
||||
while i < len(sys.argv):
|
||||
arg_in_item = False
|
||||
for item in update_items:
|
||||
if item.lower() == sys.argv[i].lower():
|
||||
kwargs[item] = sys.argv[i + 1]
|
||||
i += 2
|
||||
arg_in_item = True
|
||||
break
|
||||
if not arg_in_item:
|
||||
controlflow.invalid_argument_exit(sys.argv[i], 'gam update printer')
|
||||
result = gapi.call(cp.printers(), 'update', printerid=printerid, **kwargs)
|
||||
checkCloudPrintResult(result)
|
||||
print(f'Updated printer {printerid}')
|
||||
|
||||
|
||||
def doPrinterRegister():
|
||||
cp = buildGAPIObject('cloudprint')
|
||||
form_fields = {
|
||||
'name':
|
||||
'GAM',
|
||||
'proxy':
|
||||
'GAM',
|
||||
'uuid':
|
||||
_getValueFromOAuth('sub'),
|
||||
'manufacturer':
|
||||
GAM_AUTHOR,
|
||||
'model':
|
||||
'cp1',
|
||||
'gcp_version':
|
||||
'2.0',
|
||||
'setup_url':
|
||||
GAM_URL,
|
||||
'support_url':
|
||||
'https://groups.google.com/forum/#!forum/google-apps-manager',
|
||||
'update_url':
|
||||
GAM_RELEASES,
|
||||
'firmware':
|
||||
GAM_VERSION,
|
||||
'semantic_state': {
|
||||
'version': '1.0',
|
||||
'printer': {
|
||||
'state': 'IDLE',
|
||||
}
|
||||
},
|
||||
'use_cdd':
|
||||
True,
|
||||
'capabilities': {
|
||||
'version': '1.0',
|
||||
'printer': {
|
||||
'supported_content_type': [{
|
||||
'content_type': 'application/pdf',
|
||||
'min_version': '1.5'
|
||||
}, {
|
||||
'content_type': 'image/jpeg'
|
||||
}, {
|
||||
'content_type': 'text/plain'
|
||||
}],
|
||||
'copies': {
|
||||
'default': 1,
|
||||
'max': 100
|
||||
},
|
||||
'media_size': {
|
||||
'option': [{
|
||||
'name': 'ISO_A4',
|
||||
'width_microns': 210000,
|
||||
'height_microns': 297000
|
||||
}, {
|
||||
'name': 'NA_LEGAL',
|
||||
'width_microns': 215900,
|
||||
'height_microns': 355600
|
||||
}, {
|
||||
'name': 'NA_LETTER',
|
||||
'width_microns': 215900,
|
||||
'height_microns': 279400,
|
||||
'is_default': True
|
||||
}],
|
||||
},
|
||||
},
|
||||
},
|
||||
'tags': ['GAM', GAM_URL],
|
||||
}
|
||||
body, headers = encode_multipart(form_fields, {})
|
||||
#Get the printer first to make sure our OAuth access token is fresh
|
||||
gapi.call(cp.printers(), 'list')
|
||||
_, result = cp._http.request(
|
||||
uri='https://www.google.com/cloudprint/register',
|
||||
method='POST',
|
||||
body=body,
|
||||
headers=headers)
|
||||
result = json.loads(result.decode(UTF8))
|
||||
checkCloudPrintResult(result)
|
||||
print(f'Created printer {result["printers"][0]["id"]}')
|
||||
|
||||
|
||||
def doPrintJobResubmit():
|
||||
cp = buildGAPIObject('cloudprint')
|
||||
jobid = sys.argv[2]
|
||||
printerid = sys.argv[4]
|
||||
ssd = '{"state": {"type": "HELD"}}'
|
||||
result = gapi.call(cp.jobs(),
|
||||
'update',
|
||||
jobid=jobid,
|
||||
semantic_state_diff=ssd)
|
||||
checkCloudPrintResult(result)
|
||||
ticket = gapi.call(cp.jobs(), 'getticket', jobid=jobid, use_cjt=True)
|
||||
result = gapi.call(cp.jobs(),
|
||||
'resubmit',
|
||||
printerid=printerid,
|
||||
jobid=jobid,
|
||||
ticket=ticket)
|
||||
checkCloudPrintResult(result)
|
||||
print(
|
||||
f'Success resubmitting {jobid} as job {result["job"]["id"]} to printer {printerid}'
|
||||
)
|
||||
|
||||
|
||||
def doPrintJobSubmit():
|
||||
cp = buildGAPIObject('cloudprint')
|
||||
printer = sys.argv[2]
|
||||
content = sys.argv[4]
|
||||
form_fields = {
|
||||
'printerid': printer,
|
||||
'title': content,
|
||||
'ticket': '{"version": "1.0"}',
|
||||
'tags': ['GAM', GAM_URL]
|
||||
}
|
||||
i = 5
|
||||
while i < len(sys.argv):
|
||||
myarg = sys.argv[i].lower()
|
||||
if myarg == 'tag':
|
||||
form_fields['tags'].append(sys.argv[i + 1])
|
||||
i += 2
|
||||
elif myarg in ['name', 'title']:
|
||||
form_fields['title'] = sys.argv[i + 1]
|
||||
i += 2
|
||||
else:
|
||||
controlflow.invalid_argument_exit(sys.argv[i],
|
||||
'gam printer ... print')
|
||||
form_files = {}
|
||||
if content[:4] == 'http':
|
||||
form_fields['content'] = content
|
||||
form_fields['contentType'] = 'url'
|
||||
else:
|
||||
filepath = content
|
||||
content = os.path.basename(content)
|
||||
mimetype = mimetypes.guess_type(filepath)[0]
|
||||
if mimetype is None:
|
||||
mimetype = 'application/octet-stream'
|
||||
filecontent = fileutils.read_file(filepath, mode='rb')
|
||||
form_files['content'] = {
|
||||
'filename': content,
|
||||
'content': filecontent,
|
||||
'mimetype': mimetype
|
||||
}
|
||||
#result = gapi.call(cp.printers(), u'submit', body=body)
|
||||
body, headers = encode_multipart(form_fields, form_files)
|
||||
#Get the printer first to make sure our OAuth access token is fresh
|
||||
gapi.call(cp.printers(), 'get', printerid=printer)
|
||||
_, result = cp._http.request(uri='https://www.google.com/cloudprint/submit',
|
||||
method='POST',
|
||||
body=body,
|
||||
headers=headers)
|
||||
result = json.loads(result.decode(UTF8))
|
||||
checkCloudPrintResult(result)
|
||||
print(f'Submitted print job {result["job"]["id"]}')
|
||||
|
||||
|
||||
def doDeletePrintJob():
|
||||
cp = buildGAPIObject('cloudprint')
|
||||
job = sys.argv[2]
|
||||
result = gapi.call(cp.jobs(), 'delete', jobid=job)
|
||||
checkCloudPrintResult(result)
|
||||
print(f'Print Job {job} deleted')
|
||||
|
||||
|
||||
def doCancelPrintJob():
|
||||
cp = buildGAPIObject('cloudprint')
|
||||
job = sys.argv[2]
|
||||
ssd = '{"state": {"type": "ABORTED", "user_action_cause": {"action_code": "CANCELLED"}}}'
|
||||
result = gapi.call(cp.jobs(), 'update', jobid=job, semantic_state_diff=ssd)
|
||||
checkCloudPrintResult(result)
|
||||
print(f'Print Job {job} cancelled')
|
||||
|
||||
|
||||
def checkCloudPrintResult(result):
|
||||
if isinstance(result, bytes):
|
||||
result = result.decode(UTF8)
|
||||
if isinstance(result, str):
|
||||
try:
|
||||
result = json.loads(result)
|
||||
except ValueError:
|
||||
controlflow.system_error_exit(3, f'unexpected response: {result}')
|
||||
if not result['success']:
|
||||
controlflow.system_error_exit(
|
||||
result['errorCode'], f'{result["errorCode"]}: {result["message"]}')
|
||||
|
||||
|
||||
def doProfile(users):
|
||||
cd = buildGAPIObject('directory')
|
||||
myarg = sys.argv[4].lower()
|
||||
@@ -13236,11 +12547,6 @@ OAUTH2_SCOPES = [
|
||||
'https://www.googleapis.com/auth/classroom.guardianlinks.students'
|
||||
]
|
||||
},
|
||||
{
|
||||
'name': 'Cloud Print API',
|
||||
'subscopes': [],
|
||||
'scopes': 'https://www.googleapis.com/auth/cloudprint'
|
||||
},
|
||||
{
|
||||
'name': 'Data Transfer API',
|
||||
'subscopes': ['readonly'],
|
||||
@@ -14143,8 +13449,6 @@ def ProcessGAMCommand(args):
|
||||
doCreateOrUpdateUserSchema(True)
|
||||
elif argument in ['course', 'class']:
|
||||
doUpdateCourse()
|
||||
elif argument in ['printer', 'print']:
|
||||
doUpdatePrinter()
|
||||
elif argument == 'domain':
|
||||
doUpdateDomain()
|
||||
elif argument == 'customer':
|
||||
@@ -14192,8 +13496,6 @@ def ProcessGAMCommand(args):
|
||||
doGetUserSchema()
|
||||
elif argument in ['course', 'class']:
|
||||
doGetCourseInfo()
|
||||
elif argument in ['printer', 'print']:
|
||||
doGetPrinterInfo()
|
||||
elif argument in ['transfer', 'datatransfer']:
|
||||
doGetDataTransferInfo()
|
||||
elif argument == 'customer':
|
||||
@@ -14245,8 +13547,6 @@ def ProcessGAMCommand(args):
|
||||
doDelSchema()
|
||||
elif argument in ['course', 'class']:
|
||||
doDelCourse()
|
||||
elif argument in ['printer', 'printers']:
|
||||
doDelPrinter()
|
||||
elif argument == 'domain':
|
||||
doDelDomain()
|
||||
elif argument in ['domainalias', 'aliasdomain']:
|
||||
@@ -14325,10 +13625,6 @@ def ProcessGAMCommand(args):
|
||||
doPrintCourses()
|
||||
elif argument in ['courseparticipants', 'classparticipants']:
|
||||
doPrintCourseParticipants()
|
||||
elif argument == 'printers':
|
||||
doPrintPrinters()
|
||||
elif argument == 'printjobs':
|
||||
doPrintPrintJobs()
|
||||
elif argument in ['transfers', 'datatransfers']:
|
||||
doPrintDataTransfers()
|
||||
elif argument == 'transferapps':
|
||||
@@ -14426,35 +13722,6 @@ def ProcessGAMCommand(args):
|
||||
else:
|
||||
controlflow.invalid_argument_exit(argument, 'gam calendar')
|
||||
sys.exit(0)
|
||||
elif command == 'printer':
|
||||
if sys.argv[2].lower() == 'register':
|
||||
doPrinterRegister()
|
||||
sys.exit(0)
|
||||
argument = sys.argv[3].lower()
|
||||
if argument == 'showacl':
|
||||
doPrinterShowACL()
|
||||
elif argument == 'add':
|
||||
doPrinterAddACL()
|
||||
elif argument in ['del', 'delete', 'remove']:
|
||||
doPrinterDelACL()
|
||||
else:
|
||||
controlflow.invalid_argument_exit(argument, 'gam printer...')
|
||||
sys.exit(0)
|
||||
elif command == 'printjob':
|
||||
argument = sys.argv[3].lower()
|
||||
if argument == 'delete':
|
||||
doDeletePrintJob()
|
||||
elif argument == 'cancel':
|
||||
doCancelPrintJob()
|
||||
elif argument == 'submit':
|
||||
doPrintJobSubmit()
|
||||
elif argument == 'fetch':
|
||||
doPrintJobFetch()
|
||||
elif argument == 'resubmit':
|
||||
doPrintJobResubmit()
|
||||
else:
|
||||
controlflow.invalid_argument_exit(argument, 'gam printjob')
|
||||
sys.exit(0)
|
||||
elif command == 'report':
|
||||
gapi_reports.showReport()
|
||||
sys.exit(0)
|
||||
|
||||
@@ -236,7 +236,6 @@ API_VER_MAPPING = {
|
||||
'appsactivity': 'v1',
|
||||
'calendar': 'v3',
|
||||
'classroom': 'v1',
|
||||
'cloudprint': 'v2',
|
||||
'cloudresourcemanager': 'v2',
|
||||
'cloudresourcemanagerv1': 'v1',
|
||||
'datatransfer': 'datatransfer_v1',
|
||||
|
||||
Reference in New Issue
Block a user