I have a dictionary of providers, which will contain elements like the one below:
{ 'p_4_0_0': {'technicians': ['683707d2-be18-49b7-bf67-a32048103ca1', '23d06b03-41f4-48cc-b83f-347ebfcb3084']}, 'p_4_0_1': {'technicians': ['d226a9b6-58f3-4f94-bf81-abd4dc825dca']}, ... }
The format used for the keys is string_id_level_pid, and I use secrets.choice to get a random element where the level part of the string is equal to the current level in my loop. However, I get the following error:
Traceback (most recent call last): File
"path/to/file/graph.py",
line 122, in
generate_graph(100) File "path/to/file/graph.py",
line 112, in generate_graph
provider = providers[secrets.choice(list({k:v for (k,v) in providers.items() if (k.split('_'))[2] == str(level)}))] File
"C:\Users\\AppData\Local\Programs\Python\Python37\lib\random.py",
line 261, in choice
raise IndexError('Cannot choose from an empty sequence') from None IndexError: Cannot choose from an empty sequence [Finished in 1.564s]
The full working code is here:
import networkx as nx
import matplotlib.pyplot as plt
from random import randrange,choices,randint
from pathlib import Path
import random
import secrets
import uuid
import math
import json
import os
# ============================================================================ #
# create a technician with id and provider id
def create_technician():
return str(uuid.uuid4())
# create a provider with n technicians
def create_provider(region_id, level, number, n):
id = 'p_'+str(region_id)+'_'+str(level)+'_'+str(number)
# Create n technicians
technicians = []
for i in range(n):
technicians.append(create_technician())
return {id:{'technicians': technicians}}
def create_nmi_technicians(n):
technicians = []
for i in range(n):
technicians.append(create_technician())
return technicians
# Create report with parents + technician
def create_report(device_id, level, technician, parents):
return {'id': device_id, 'level': level, 'technician': technician, 'parents': parents}
# n = number of field devices
def generate_graph(num_field_devices):
max_chain_length = int(2*math.log(num_field_devices, 10))
## Info ##
# ====== #
# Field level = 0
# NMI = max_chain_length-1
nmi_level = str(max_chain_length-1)
regions = {
'USA': {'id': '1', 'NMI': {'level': nmi_level, 'acronym': 'NIST', 'technicians': create_nmi_technicians(5)}},
'UK': {'id': '2', 'NMI': {'level': nmi_level, 'acronym': 'NPL', 'technicians': create_nmi_technicians(4)}},
'China': {'id': '3', 'NMI': {'level': nmi_level, 'acronym': 'NIM', 'technicians': create_nmi_technicians(3)}},
'France': {'id': '4', 'NMI': {'level': nmi_level, 'acronym': 'LNE', 'technicians': create_nmi_technicians(3)}}
}
# For each region, create a set of
# 1 to m calibration service
# providers for each level up to
# the field level
for region, data in regions.items():
# Create providers dict
providers = {}
# For range between field (0) and
# max_chain_length-2, create providers
for i in range(0, max_chain_length-1):
# Choose between 2 and 5 providers
m = randint(2, 5)
x = 0
for j in range(m):
# create provider with 1-3 technicians
providers.update(create_provider(data['id'], i, x, randint(1,3)))
x = x + 1
# Add providers to region
data.update({'providers': providers})
#print(json.dumps(regions, indent=4))
# Cool, now this is done, create the calibration
# reports for the chain!
devices = {}
for level in range(max_chain_length):
devices.update({level: []})
# Field level
if level == 0:
for i in range(num_field_devices):
devices[level].append(str(uuid.uuid4()))
else:
k = int(math.pow((2/3), level) * num_field_devices)
for i in range(k):
devices[level].append(str(uuid.uuid4()))
# Create reports for these devices with parents + technician
reports = {}
for level,devs in devices.items():
for device in devs:
if level == 0:
# Choose 2-3 parents from upper level
parents = choices(devices[level+1], k=randrange(2,4))
elif level == max_chain_length-1:
# NMI level has no parents
parents = []
else:
# Choose 1-2 parents from upper level
parents = choices(devices[level+1], k=randrange(1,3))
# Choose random region
region = regions[secrets.choice(list(regions))]
# Choose random provider at same level
providers = region['providers']
provider = providers[secrets.choice(list({k:v for (k,v) in providers.items() if (k.split('_'))[2] == str(level)}))]
# Choose technician at the same level
technician = secrets.choice(provider['technicians'])
reports.update({'id': create_report(device, level, technician, parents)})
print(reports)
## Run ##
# ===== #
generate_graph(100)
EDIT: the last element in providers is {} (empty dict) - what is the reason for this?
The highest level has its technicians in the NMI region, not in a provider dict. The solution here was the following:
# Choose random region
region = regions[secrets.choice(list(regions))]
# If NMI, use NMI technician, otherwise
# choose a provider from the level
if level == max_chain_length-1:
technician = secrets.choice(region['NMI']['technicians'])
else:
# Choose random provider at same level
providers = region['providers']
provider = providers[secrets.choice(list({k:v for (k,v) in providers.items() if (k.split('_'))[2] == str(level)}))]
# Choose technician at the same level
technician = secrets.choice(provider['technicians'])
Related
I've been searching through stackoverflow and other various sites, but I've been unable to resolve this error for about a week now.
I'm trying the get the minimum and maximum values from each country within the dictionary. The key of the dictionary is the region. I'm unsure of where the type error is but, I'd appreciate it if someone could help.
Here's the error:
min_tup, max_tup = get_min_max(D,region,option)
File "proj08.py", line 107, in get_min_max
return min[0], max[0]
UnboundLocalError: local variable 'min' referenced before assignment
Here's the sample input:
Region,option: North America , 2
Here's the documentation explaining the function and .csv
https://www.cse.msu.edu/~cse231/Online/Projects/Project08/Project08.pdf
https://www.cse.msu.edu/~cse231/Online/Projects/Project08/data_short.csv
Here's the code:
import csv
from operator import itemgetter
# do NOT import sys
REGION_LIST = ['East Asia & Pacific',
'Europe & Central Asia',
'Latin America & Caribbean',
'Middle East & North Africa',
'North America',
'South Asia',
'Sub-Saharan Africa']
PROMPT = "\nSpecify a region from this list or 'q' to quit -- \nEast
Asia & Pacific,Europe & Central Asia,Latin America & Caribbean,Middle
East & North
Africa,North America,South Asia,Sub-Saharan Africa: "
def open_file():
# Opens a file
while True:
try:
file = input("Input a file: ")
fp = open(file, "r")
return fp
except FileNotFoundError:
print("Invalid filename, please try again.")
def read_file(fp):
# Sets read Csv file to a variable
reader = csv.reader(fp)
# Skips the header
next(reader, None)
# Country List
country_list = []
# sets a dictionary
Dict = dict()
for line in reader:
try:
skipper = ""
if skipper in line:
continue
else:
region = line[6]
country = line[0].strip()
electricty = float(line[2])
fertility = float(line[3])
gdp = float(line[4])
life_expectancy = float(line[5])
country_list = [country, electricty, fertility, GDP,
life_expectancy]
if region in Dict.keys():
Dict[region].append(country_list)
elif region not in Dict.keys():
Dict[region] = [country_list]
else:
continue
except KeyError:
continue
except ValueError:
continue
return Dict
def get_min_max(Dict, region, option):
lis = []
for k, v in Dict.items():
if region in k[0]:
if option == 1:
electricity = v[1]
tup = tuple(k, electricity)
lis.append(tup)
min = sorted(lis, key=itemgetter(1))
max = sorted(lis, key=itemgetter(1), reverse=True)
if option == 2:
fertility = v[2]
tup = tuple(k, fertility)
lis.append(tup)
min = sorted(lis, key=itemgetter(1))
max = sorted(lis, key=itemgetter(1), reverse=True)
if option == 3:
gdp = v[3]
tup = tuple(k, gdp)
lis.append(tup)
min = sorted(lis, key=itemgetter(1))
max = sorted(lis, key=itemgetter(1), reverse=True)
if option == 4:
life_expectancy = v[4]
tup = tuple(k, life_expectancy)
lis.append(tup)
min = sorted(lis, key=itemgetter(1))
max = sorted(lis, key=itemgetter(1), reverse=True)
return min[0], max[0]
def display_all_countries(D, region):
if region in REGION_LIST:
if region == 'all':
print("\nDisplaying {} Region:\n".format(region))
print("{:32s}{:>20s}{:>20s}{:>17s}{:>18s}".format(
"Country", "Electricity Access", "Fertility rate", "GDP
per capita", "Life expectancy"))
for k, v in D.items():
if region in v[0]:
country = v[0]
electricity = v[1]
fertility = v[2]
gdp = v[3]
life = v[4]
tup = (country, electricity, fertility, gdp, life)
sorted(tup, key=itemgetter(0), reverse=True)
print("{:32s}{:>20.2f}{:>20.2f}{:>17.2f}
{:>18.2f}".format(
tup[0], tup[1], tup[2], tup[3], tup[4]))
if region not in REGION_LIST:
return None
def get_top10(D):
pass
def display_options():
"""
DO NOT CHANGE
Display menu of options for program
"""
OPTIONS = """\nMenu
1: Minimum and Maximum Countries Access to Electricity
2: Minimum and Maximum Countries Fertility Rate
3: Minimum and Maximum Countries GDP per Capita
4: Minimum and Maximum Countries Life Expectancy
5: List of countries in a region
6: Top 10 Countries in the world by GDP per Capita\n"""
print(OPTIONS)
def main():
file = open_file()
# while True:
# if user == 'East Asia & Pacific' or user == 'Europe &
Central Asia' or user == 'Middle East & North Africa' or user ==
'Latin America & Caribbean' or user == 'North America' or user ==
'South Asia' or user == 'Sub-Saharan Africa':
# print("\nRegion: ".format(user))
# display_options()
# if user == "Q" or user == "q":
# break
# else:
# user = input(PROMPT)
region = 'North America'
option = '2'
superD = read_file(file)
mina = get_min_max(superD, region, option)
#print(mina)
if __name__ == '__main__':
main()
The error is telling you that you can't use unpacking assignment such as
x, y = function()
Because the function returned something that can't be unpacked (None, in this case)
This means that your function returned None somehow. We can't say for sure without a reusable example, but I would guess that its because of the first if condition in your function, which can return None.
Although it is allowed, it is generally not a great idea to have multiple different return types in a python function. This is because the caller has to know how to handle different things that the function might do, instead of being able to trust that the function will work and give them a good answer (assuming of course, that they are using correct inputs.)
I'm trying to use the function 'set_disp_time' to change the disp_time value of every 'workshop' object from undefined to a certain number, depending on a formula.
The formula can take 2 forms depending from an if statement, but the condition for entering the statement returns false even when it should return true!
This is the code:
Class that calls the fuction:
from loader import Loader
loader_ = Loader(r'C:\Users\damia\OneDrive\Desktop\logistic management tool\cycles_sample.xlsx',
r'C:\Users\damia\OneDrive\Desktop\logistic management tool\demand_sample.xlsx',
r'C:\Users\damia\OneDrive\Desktop\logistic management tool\bom_sample.xlsx',
r'C:\Users\damia\OneDrive\Desktop\logistic management tool\workshops_sample.xlsx')
class Plant:
def __init__(self, loader):
self.loader = loader
self.workshops = self.loader.get_workshops()
for ws in self.workshops:
print('workshop automation level: ', ws.automation)
print('checks if the workshop automation is table: ', str(ws.automation) == 'table')
# computes disposable times
for workshop in self.workshops:
workshop.set_disp_time()
plant = Plant(loader_)
class Workshop:
def __init__(self, name, shifts, shift_dur, pauses, pause_dur, placing, type_, uptime):
self.name = name
self.shifts = shifts
self. shift_dur = shift_dur
self.pauses = pauses
self.pause_dur = pause_dur
self.placing = placing
self.type_ = type_
self.uptime = uptime
self.parts = []
self.automation = set()
self.disp_time = 'undefined'
def set_part(self, part):
for phase in part.phases:
if phase.placings > 0:
self.automation.add('auto')
elif phase.placings == 0 and phase.machining != phase.operator:
self.automation.add('machine')
elif phase.placings == 0 and phase.machining == phase.operator:
self.automation.add('table')
else:
raise Exception('Undefined type for workshop, part, phase: ', self.name, part.name, phase.seq)
if len(self.automation) != 1:
raise Exception('more that 1 kind of automation')
self.parts.append(part)
# computes workshop disposable time
def set_disp_time(self):
print('inside set function')
print(self.automation)
print(self.automation == set('auto'))
if self.automation == set('table'):
self.disp_time = self.shifts * self.shift_dur * 60 * self.uptime - self.pauses * self.pause_dur
elif self.automation == set('machine') or self.automation == set('auto'):
self.disp_time = self.shifts * self.shift_dur * 60 * self.uptime
else:
raise Exception('Undefined disposable time for: ', self.name)
There's also a class that loads data from excel, but it shouldn't give any problem, since the workshop objects are created correctly:
import pandas as pd
from iteration_utilities import duplicates, unique_everseen
from workshop import Workshop
class Phase:
def __init__(self, seq, workshop, machining, operator, placings, setup):
self.seq = seq
self.workshop = workshop
self.machining = machining
self.operator = operator
self.placings = placings
self.setup = setup
class Part:
def __init__(self, name, phases, workshop):
self.name = name
self.phases = phases
self.workshop = workshop
self.demand = 'undefined'
self.downstream_bom = 'undefined'
# check if all seq are unique and in sequence
if not all(x.seq < y.seq for x, y in zip(self.phases, self.phases[1:])):
raise Exception('Unsorted phases in part: ', self.name)
def set_demand(self, demand):
self.demand = demand
def set_downstream_bom(self, bom):
self.downstream_bom = bom
class Loader:
def __init__(self, cycles_file, demand_file, bom_file, workshops_file):
self.cycles_file = cycles_file
self.demand_file = demand_file
self.bom_file = bom_file
self.workshops_file = workshops_file
self.workshops = []
cycles = pd.read_excel(self.cycles_file, sheet_name=None)
# checks if all part names are unique
cycles_names = []
for sheet in cycles:
cycles_names.append(sheet)
if list(duplicates(cycles_names)):
raise Exception('Multiple parts names in cycles file: ', list(duplicates(cycles_names)))
# list of parts sheets
sheets = []
for sheet in cycles:
sheets.append(cycles[sheet])
# fillna
sheets = [sheets[i].fillna(0) for i in range(len(sheets))]
# drops useless 2nd row
sheets = [sheets[i].drop([0]) for i in range(len(sheets))]
# drops useless columns
sheets = [sheets[i].drop(['Unnamed: 1', 'T mac (min/pz)', 'Unnamed: 4', 'Unnamed: 5'], axis=1) for i in range(len(sheets))]
# list of parts names
parts = []
for sheet in sheets:
part_name = sheet.columns[0]
workshops_set = set()
phases_list = []
for i in range(len(sheet.index)):
seq = sheet.iloc[i][0]
workshop = sheet.iloc[i][1]
workshops_set.add(workshop)
machining = sheet.iloc[i][2]
operator = sheet.iloc[i][3]
placings = sheet.iloc[i][4]
setup = sheet.iloc[i][5]
# checks placings coherence
if (placings > 0 and setup > 0) or (placings > 0 and operator > 0):
raise Exception('Placing coherence error in part, phase: ', self.name, seq)
phase = Phase(seq, workshop, machining, operator, placings, setup)
phases_list.append(phase)
for workshop in workshops_set:
same_workshop_phases = []
for phase in phases_list:
if workshop == phase.workshop:
same_workshop_phases.append(phase)
part = Part(part_name, same_workshop_phases, workshop)
parts.append(part)
demand_data = pd.read_excel(self.demand_file)
# checks for multiple products
if list(duplicates(demand_data)):
raise Exception('Multiple parts in demand file: ', list(duplicates(demand_data)))
# demand assignment
for part in parts:
for col in demand_data.columns:
if part.name == col:
part.set_demand(demand_data[col])
bom_data = pd.read_excel(self.bom_file)
bom_data = bom_data.fillna(0)
# changes index name from numbers to parts
new_indexes = []
for item in bom_data['Unnamed: 0']:
new_indexes.append(item)
bom_data.index = new_indexes
# deletes parts names column
bom_data = bom_data.drop(['Unnamed: 0'], axis=1)
# checks for multiple parts in rows and columns
if list(duplicates(bom_data.columns)):
raise Exception('Multiple parts in BoM columns: ', list(duplicates(bom_data.columns)))
if list(duplicates(bom_data.index)):
raise Exception('Multiple parts in BoM rows: ', list(duplicates(bom_data.index)))
# checks if there are reciprocal dependencies
coordinates = []
for column in bom_data.columns:
for row in bom_data.index:
if row != column and bom_data.at[row, column] > 0:
coordinates.append({row, column})
duplicates_list = list(duplicates(coordinates))
if duplicates_list:
raise Exception('Reciprocal dependencies in the BoM: ', duplicates_list)
# sets downstream BoM
for part in parts:
part.set_downstream_bom(bom_data.loc[part.name])
# checks coherence of parts data
if len(list(unique_everseen(list(bom_data.columns) + list(bom_data.index)))) != len(sheets):
raise Exception('Incoherent data about parts names in the BoM')
workshops_data = pd.read_excel(self.workshops_file, sheet_name=None)
# checks if there are turns and turn durations
for workshop in workshops_data:
if int(workshops_data[workshop]['Shifts']) == 0:
raise Exception('Missing shifts in workshop: ', workshop)
if float(workshops_data[workshop]['Shift duration (h)']) == 0:
raise Exception('Missing Shift duration in workshop: ', workshop)
# checks for multiple names
if list(duplicates(workshops_data)):
raise Exception('Duplicate names in workshops data: ', list(duplicates(workshops_data)))
# checks if all the workshops in the parts are present in the workshop file
for part in parts:
for phase in part.phases:
if phase.workshop not in workshops_data:
raise Exception('workshop in cycles not found in workshops file: ', phase.workshop)
# creates workshop obj
for workshop in workshops_data:
name = workshop
shifts = int(workshops_data[workshop]['Shifts'])
shift_dur = float(workshops_data[workshop]['Shift duration (h)'])
pauses = int(workshops_data[workshop]['Pauses/shift'])
pause_dur = float(workshops_data[workshop]['Pause duration (min)'])
placing = float(workshops_data[workshop]['Placing duration (min)'])
type_ = str(workshops_data[workshop]['Type'])
uptime = float(workshops_data[workshop]['uptime'])
workshop = Workshop(name, shifts, shift_dur, pauses, pause_dur, placing, type_, uptime)
self.workshops.append(workshop)
# setting parts for workshops
for part in parts:
for workshop in self.workshops:
if workshop.name == part.workshop:
workshop.set_part(part)
def get_workshops(self):
return self.workshops
This is the result I get:
workshop automation level: {'auto'}
checks if the workshop automation is table: False
workshop automation level: {'machine'}
checks if the workshop automation is table: False
workshop automation level: {'machine'}
checks if the workshop automation is table: False
workshop automation level: {'table'}
checks if the workshop automation is table: False
workshop automation level: {'table'}
checks if the workshop automation is table: False
workshop automation level: {'table'}
checks if the workshop automation is table: False
workshop automation level: {'table'}
checks if the workshop automation is table: False
workshop automation level: {'table'}
checks if the workshop automation is table: False
inside set function
{'auto'}
False
Traceback (most recent call last):
File "C:\Users\damia\PycharmProjects\logistic_management_tool\plant.py", line 25, in
plant = Plant(loader_)
File "C:\Users\damia\PycharmProjects\logistic_management_tool\plant.py", line 22, in init
workshop.set_disp_time()
File "C:\Users\damia\PycharmProjects\logistic_management_tool\workshop.py", line 48, in set_disp_time
raise Exception('Undefined disposable time for: ', self.name)
Exception: ('Undefined disposable time for: ', 'clav acciaio')
I'm using the python-fedex module as a light wrapper for the FedEx SOAP API. As part of this, I'm trying to set up a basic example of an international shipment, but I'm getting stuck with the following error message:
fedex.base_service.FedexError: Customs Value is required. (Error code: 2033)
I believe I need to add the products I ship as commodities, incl. their customs value - but I struggle to get this to work. I found this link with some guidance (from C#), but I was unable to get it to work in Python. Any inputs are appreciated!
My code is below:
# !/usr/bin/env python
"""
This example shows how to create a shipment and generate a waybill as output. The variables populated below
represents the minimum required values. You will need to fill all of these, or
risk seeing a SchemaValidationError exception thrown.
Near the bottom of the module, you'll see some different ways to handle the
label data that is returned with the reply.
"""
import logging
import binascii
import datetime
import sys, os
from example_config import CONFIG_OBJ
from fedex.services.ship_service import FedexProcessShipmentRequest
# What kind of file do you want this example to generate?
# Valid choices for this example are PDF, PNG
GENERATE_IMAGE_TYPE = 'PDF'
# Un-comment to see the response from Fedex printed in stdout.
logging.basicConfig(stream=sys.stdout, level=logging.INFO)
# This is the object that will be handling our shipment request.
# We're using the FedexConfig object from example_config.py in this dir.
customer_transaction_id = "*** ShipService Request v17 using Python ***" # Optional transaction_id
shipment = FedexProcessShipmentRequest(CONFIG_OBJ, customer_transaction_id=customer_transaction_id)
# This is very generalized, top-level information.
# REGULAR_PICKUP, REQUEST_COURIER, DROP_BOX, BUSINESS_SERVICE_CENTER or STATION
shipment.RequestedShipment.DropoffType = 'BUSINESS_SERVICE_CENTER'
# See page 355 in WS_ShipService.pdf for a full list. Here are the common ones:
# STANDARD_OVERNIGHT, PRIORITY_OVERNIGHT, FEDEX_GROUND, FEDEX_EXPRESS_SAVER,
# FEDEX_2_DAY, INTERNATIONAL_PRIORITY, SAME_DAY, INTERNATIONAL_ECONOMY
shipment.RequestedShipment.ServiceType = 'INTERNATIONAL_PRIORITY'
# What kind of package this will be shipped in.
# FEDEX_BOX, FEDEX_PAK, FEDEX_TUBE, YOUR_PACKAGING, FEDEX_ENVELOPE
shipment.RequestedShipment.PackagingType = 'FEDEX_ENVELOPE'
# Shipper contact info.
shipment.RequestedShipment.Shipper.Contact.PersonName = 'Shipper Name'
shipment.RequestedShipment.Shipper.Contact.CompanyName = 'Shipper Company'
shipment.RequestedShipment.Shipper.Contact.PhoneNumber = '004512345678'
# Shipper address.
shipment.RequestedShipment.Shipper.Address.StreetLines = ['Shipper Address']
shipment.RequestedShipment.Shipper.Address.City = 'City'
shipment.RequestedShipment.Shipper.Address.StateOrProvinceCode = ''
shipment.RequestedShipment.Shipper.Address.PostalCode = '8270'
shipment.RequestedShipment.Shipper.Address.CountryCode = 'DK'
shipment.RequestedShipment.Shipper.Address.Residential = False
# Recipient contact info.
shipment.RequestedShipment.Recipient.Contact.PersonName = 'US customer X'
shipment.RequestedShipment.Recipient.Contact.CompanyName = 'US company X'
shipment.RequestedShipment.Recipient.Contact.PhoneNumber = '0123456789'
# Recipient address
shipment.RequestedShipment.Recipient.Address.StreetLines = ['668 MURRAY AVE SE']
shipment.RequestedShipment.Recipient.Address.City = 'ROANOKE'
shipment.RequestedShipment.Recipient.Address.StateOrProvinceCode = 'VA'
shipment.RequestedShipment.Recipient.Address.PostalCode = '24013'
shipment.RequestedShipment.Recipient.Address.CountryCode = 'US'
# This is needed to ensure an accurate rate quote with the response. Use AddressValidation to get ResidentialStatus
shipment.RequestedShipment.Recipient.Address.Residential = False
shipment.RequestedShipment.EdtRequestType = 'NONE'
# Senders account information
shipment.RequestedShipment.ShippingChargesPayment.Payor.ResponsibleParty.AccountNumber = CONFIG_OBJ.account_number
# Who pays for the shipment?
# RECIPIENT, SENDER or THIRD_PARTY
shipment.RequestedShipment.ShippingChargesPayment.PaymentType = 'SENDER'
# Specifies the label type to be returned.
# LABEL_DATA_ONLY or COMMON2D
shipment.RequestedShipment.LabelSpecification.LabelFormatType = 'COMMON2D'
# Specifies which format the label file will be sent to you in.
# DPL, EPL2, PDF, PNG, ZPLII
shipment.RequestedShipment.LabelSpecification.ImageType = GENERATE_IMAGE_TYPE
# To use doctab stocks, you must change ImageType above to one of the
# label printer formats (ZPLII, EPL2, DPL).
# See documentation for paper types, there quite a few.
shipment.RequestedShipment.LabelSpecification.LabelStockType = 'PAPER_7X4.75'
# This indicates if the top or bottom of the label comes out of the
# printer first.
# BOTTOM_EDGE_OF_TEXT_FIRST or TOP_EDGE_OF_TEXT_FIRST
# Timestamp in YYYY-MM-DDThh:mm:ss format, e.g. 2002-05-30T09:00:00
shipment.RequestedShipment.ShipTimestamp = datetime.datetime.now().replace(microsecond=0).isoformat()
# BOTTOM_EDGE_OF_TEXT_FIRST, TOP_EDGE_OF_TEXT_FIRST
shipment.RequestedShipment.LabelSpecification.LabelPrintingOrientation = 'TOP_EDGE_OF_TEXT_FIRST'
# Delete the flags we don't want.
# Can be SHIPPING_LABEL_FIRST, SHIPPING_LABEL_LAST or delete
if hasattr(shipment.RequestedShipment.LabelSpecification, 'LabelOrder'):
del shipment.RequestedShipment.LabelSpecification.LabelOrder # Delete, not using.
# Create Weight, in pounds.
package1_weight = shipment.create_wsdl_object_of_type('Weight')
package1_weight.Value = 1.0
package1_weight.Units = "LB"
# Create PackageLineItem
package1 = shipment.create_wsdl_object_of_type('RequestedPackageLineItem')
# BAG, BARREL, BASKET, BOX, BUCKET, BUNDLE, CARTON, CASE, CONTAINER, ENVELOPE etc..
package1.PhysicalPackaging = 'ENVELOPE'
package1.Weight = package1_weight
# Add a signature option for the package using SpecialServicesRequested or comment out.
# SpecialServiceTypes can be APPOINTMENT_DELIVERY, COD, DANGEROUS_GOODS, DRY_ICE, SIGNATURE_OPTION etc..
package1.SpecialServicesRequested.SpecialServiceTypes = 'SIGNATURE_OPTION'
# SignatureOptionType can be ADULT, DIRECT, INDIRECT, NO_SIGNATURE_REQUIRED, SERVICE_DEFAULT
package1.SpecialServicesRequested.SignatureOptionDetail.OptionType = 'SERVICE_DEFAULT'
# This adds the RequestedPackageLineItem WSDL object to the shipment. It
# increments the package count and total weight of the shipment for you.
shipment.add_package(package1)
# If you want to make sure that all of your entered details are valid, you
# can call this and parse it just like you would via send_request(). If
# shipment.response.HighestSeverity == "SUCCESS", your shipment is valid.
# print(shipment.send_validation_request())
# Fires off the request, sets the 'response' attribute on the object.
shipment.send_request()
Your need to add more information.
Insert the following codes before shipment.send_request(), then try again.
shipment.RequestedShipment.CustomsClearanceDetail.CustomsValue.Currency = 'USD'
shipment.RequestedShipment.CustomsClearanceDetail.CustomsValue.Amount = 1.0
shipment.RequestedShipment.CustomsClearanceDetail.DutiesPayment.PaymentType = 'SENDER'
shipment.RequestedShipment.CustomsClearanceDetail.DutiesPayment.Payor.ResponsibleParty.AccountNumber = CONFIG_OBJ.account_number
commodity1 = shipment.create_wsdl_object_of_type('Commodity')
commodity1.Name = 'book'
commodity1.NumberOfPieces = 1
commodity1.Description = '1'
commodity1.CountryOfManufacture = 'CN'
commodity1.HarmonizedCode = '123456789'
commodity1.Quantity = 1.0
commodity1.QuantityUnits = 'EA'
commodity1.Weight.Value = 1.0
commodity1.Weight.Units = "LB"
commodity1.CustomsValue.Currency = 'USD'
commodity1.CustomsValue.Amount = 1.0
commodity1.UnitPrice.Currency = 'USD'
commodity1.UnitPrice.Amount = 1.0
shipment.RequestedShipment.CustomsClearanceDetail.Commodities = [commodity1]
I have added a full international shipment example below, which solves this:
"""
This example shows how to create an international shipment and generate a waybill as output.
The example takes outset in a real practical use case, where electronic trade documents are
used and an existing PDF commercial invoice is added along with product descriptions via ETD.
Further, it adds event notifications to allow for emails to be sent to the end recipient.
The script is comprised of a FedExLabelHelper class with all core functions, and a use case
example with minimal dummy data
"""
from example_config import CONFIG_OBJ
from pathlib import Path
import binascii
import datetime
from fedex.services.ship_service import FedexProcessShipmentRequest
# ----------------------------------------------------
# FedEx class for creating shipments
class FedexLabelHelper:
mCommodities = []
def __init__(self):
pass
# ----------------------------------------------------
# set overall shipment configuration
def setShipmentConfig(
self,
CONFIG_OBJ,
invoice_info,
cust_tran_id="*** ShipService Request v17 using Python ***",
dropoffType="BUSINESS_SERVICE_CENTER",
shippingPaymentType="SENDER",
labelFormatType="COMMON2D",
labelSpecificationImageType="PDF",
labelSpecificationStockType="PAPER_7X4.75",
labelPrintingOrientation="TOP_EDGE_OF_TEXT_FIRST",
LabelOrder="SHIPPING_LABEL_FIRST",
):
self.invoice_info = invoice_info
self.dropoffType = dropoffType
self.serviceType = "INTERNATIONAL_PRIORITY" if invoice_info["ShippingExpress"] == True else "INTERNATIONAL_ECONOMY"
self.mCommodities.clear()
self.CONFIG_OBJ = CONFIG_OBJ
self.shipment = FedexProcessShipmentRequest(CONFIG_OBJ, customer_transaction_id=cust_tran_id)
self.shipment.RequestedShipment.DropoffType = dropoffType
self.shipment.RequestedShipment.ServiceType = self.serviceType
self.shipment.RequestedShipment.ShippingChargesPayment.Payor.ResponsibleParty.AccountNumber = CONFIG_OBJ.account_number
self.shipment.RequestedShipment.ShippingChargesPayment.Payor.ResponsibleParty.Address.CountryCode = "DK"
self.shipment.RequestedShipment.ShippingChargesPayment.PaymentType = shippingPaymentType
labelSpecification = self.shipment.create_wsdl_object_of_type("LabelSpecification")
labelSpecification.LabelFormatType = labelFormatType
labelSpecification.LabelStockType = labelSpecificationStockType
labelSpecification.ImageType = labelSpecificationImageType
labelSpecification.LabelOrder = LabelOrder
labelSpecification.LabelPrintingOrientation = labelPrintingOrientation
self.shipment.RequestedShipment.LabelSpecification = labelSpecification
# ----------------------------------------------------
# set sender information
def setSenderInfo(self, sender):
self.shipment.RequestedShipment.Shipper.Contact.PersonName = sender["Name"]
self.shipment.RequestedShipment.Shipper.Contact.CompanyName = sender["Company"]
self.shipment.RequestedShipment.Shipper.Contact.PhoneNumber = sender["Phone"]
self.shipment.RequestedShipment.Shipper.Contact.EMailAddress = sender["Email"]
self.shipment.RequestedShipment.Shipper.Address.StreetLines = sender["Address"]
self.shipment.RequestedShipment.Shipper.Address.City = sender["City"]
self.shipment.RequestedShipment.Shipper.Address.StateOrProvinceCode = sender["Region"]
self.shipment.RequestedShipment.Shipper.Address.PostalCode = sender["Zip"]
self.shipment.RequestedShipment.Shipper.Address.CountryCode = sender["CountryCode"]
self.shipment.RequestedShipment.Shipper.Address.Residential = sender["Residential"]
ti = self.shipment.create_wsdl_object_of_type("TaxpayerIdentification")
ti.Number = sender["VAT"]
ti.TinType = "BUSINESS_NATIONAL"
self.shipment.RequestedShipment.Shipper.Tins = ti
# ----------------------------------------------------
# upload all documents (invoice and product information)
def upload_all_documents(self):
doc_ids = []
doc_ids.append(self.upload_document(self.invoice_info["InvoicePath"], "COMMERCIAL_INVOICE"))
for pdf in self.invoice_info["Pdfs"]:
doc_ids.append(self.upload_document(pdf, "OTHER"))
return doc_ids
# ----------------------------------------------------
# function for uploading documents as electronic trade documents and getting the response doc IDs
def upload_document(self, path, type):
from fedex.services.document_service import FedexDocumentServiceRequest
# specify prefix for use in attachment naming
if type == "COMMERCIAL_INVOICE":
prefix = "invoice_"
else:
prefix = "product_description_"
uploadRequest = FedexDocumentServiceRequest(self.CONFIG_OBJ)
uploadRequest.OriginCountryCode = "DK"
uploadRequest.DestinationCountryCode = self.shipment.RequestedShipment.Recipient.Address.CountryCode
uploadRequest.Usage = "ELECTRONIC_TRADE_DOCUMENTS"
clientdetails = uploadRequest.create_wsdl_object_of_type("ClientDetail")
clientdetails.AccountNumber = self.CONFIG_OBJ.account_number
clientdetails.MeterNumber = self.CONFIG_OBJ.meter_number
uploadRequest.ClientDetail = clientdetails
webAuthDetails = uploadRequest.create_wsdl_object_of_type("WebAuthenticationDetail")
webAuthDetails.ParentCredential.Key = self.CONFIG_OBJ.key
webAuthDetails.ParentCredential.Password = self.CONFIG_OBJ.password
webAuthDetails.UserCredential.Key = self.CONFIG_OBJ.key
webAuthDetails.UserCredential.Password = self.CONFIG_OBJ.password
uploadRequest.WebAuthenticationDetail = webAuthDetails
docdetails = uploadRequest.create_wsdl_object_of_type("UploadDocumentDetail")
docdetails.LineNumber = 1
docdetails.DocumentType = type
docdetails.FileName = prefix + path
fileContent = open(path, "rb").read()
fileBase64 = binascii.b2a_base64(fileContent)
docdetails.DocumentContent = fileBase64.decode("cp1250")
uploadRequest.Documents = docdetails
uploadRequest.send_request()
doc_id = uploadRequest.response.DocumentStatuses[0].DocumentId
return doc_id
# ----------------------------------------------------
# set recipient information
def setRecipientInfo(self, recipient):
self.shipment.RequestedShipment.Recipient.Contact.PersonName = recipient["Name"]
self.shipment.RequestedShipment.Recipient.Contact.CompanyName = recipient["Company"]
self.shipment.RequestedShipment.Recipient.Contact.PhoneNumber = recipient["Phone"]
self.shipment.RequestedShipment.Recipient.Contact.EMailAddress = recipient["Email"]
self.shipment.RequestedShipment.Recipient.Address.StreetLines = recipient["Address"]
self.shipment.RequestedShipment.Recipient.Address.City = recipient["City"]
self.shipment.RequestedShipment.Recipient.Address.StateOrProvinceCode = recipient["Region"]
self.shipment.RequestedShipment.Recipient.Address.PostalCode = recipient["Zip"]
self.shipment.RequestedShipment.Recipient.Address.CountryCode = recipient["CountryCode"]
self.shipment.RequestedShipment.Recipient.Address.Residential = recipient["Residential"]
ti = self.shipment.create_wsdl_object_of_type("TaxpayerIdentification")
ti.Number = recipient["VAT"]
ti.TinType = "BUSINESS_NATIONAL"
self.shipment.RequestedShipment.Recipient.Tins = ti
# ----------------------------------------------------
# add "commercial invoice" reference as the only commodity
def add_ci_commodity(self):
self.addCommodity(
cCustomsValueAmnt=self.invoice_info["Value"],
cCustomsValueCurrency=self.invoice_info["Currency"],
cWeightValue=self.invoice_info["Weight"],
cDescription="See attached commercial invoice",
cQuantity=self.invoice_info["Quantity"],
cExportLicenseNumber=self.shipment.RequestedShipment.Shipper.Tins.Number,
cPartNumber=1,
)
# ----------------------------------------------------
# add commodity to shipment (for now, just add 1 commodity to refer to attached CI)
def addCommodity(
self, cCustomsValueAmnt, cCustomsValueCurrency, cWeightValue, cDescription, cQuantity, cExportLicenseNumber, cPartNumber,
):
commodity = self.shipment.create_wsdl_object_of_type("Commodity")
commodity.NumberOfPieces = str(cQuantity)
commodity.Description = cDescription
commodity.Quantity = cQuantity
commodity.QuantityUnits = "EA"
commodity.ExportLicenseNumber = cExportLicenseNumber
commodity.PartNumber = cPartNumber
commodity.CountryOfManufacture = "DK"
mCustomsValue = self.shipment.create_wsdl_object_of_type("Money")
mCustomsValue.Amount = cCustomsValueAmnt
mCustomsValue.Currency = cCustomsValueCurrency
commodity.CustomsValue = mCustomsValue
commodity_weight = self.shipment.create_wsdl_object_of_type("Weight")
commodity_weight.Value = cWeightValue
commodity_weight.Units = "KG"
commodity.Weight = commodity_weight
munitPrice = self.shipment.create_wsdl_object_of_type("Money")
munitPrice.Amount = float(round((cCustomsValueAmnt / cQuantity), 2))
munitPrice.Currency = cCustomsValueCurrency
commodity.UnitPrice = munitPrice
self.mCommodities.append(commodity)
# ----------------------------------------------------
# add package to shipment
def set_packaging_info(self):
weight = self.invoice_info["Weight"]
type = "BOX" if weight > 0.5 else "ENVELOPE"
weight_final = float(round(weight + 0.2, 2)) if weight > 0.5 else 0.4
self.addShippingPackage(packageWeight=weight_final, physicalPackagingType=type, packagingType=f"FEDEX_{type}")
# ----------------------------------------------------
# add package to shipment
def addShippingPackage(self, packageWeight, physicalPackagingType, packagingType, packageWeightUnit="KG"):
package_weight = self.shipment.create_wsdl_object_of_type("Weight")
package_weight.Value = packageWeight
package_weight.Units = packageWeightUnit
package = self.shipment.create_wsdl_object_of_type("RequestedPackageLineItem")
package.PhysicalPackaging = physicalPackagingType
package.Weight = package_weight
self.shipment.add_package(package)
self.shipment.RequestedShipment.TotalWeight = package_weight
self.shipment.RequestedShipment.PackagingType = packagingType
# ----------------------------------------------------
# add information on duties
def setDutiesPaymentInfo(self):
mParty = self.shipment.create_wsdl_object_of_type("Party")
mParty.AccountNumber = self.CONFIG_OBJ.account_number
mParty.Address = self.shipment.RequestedShipment.Recipient.Address
mPayor = self.shipment.create_wsdl_object_of_type("Payor")
mPayor.ResponsibleParty = mParty
mPayment = self.shipment.create_wsdl_object_of_type("Payment")
mPayment.PaymentType = "RECIPIENT" # change if sender should pay duties
mPayment.Payor = mPayor
mCustomsValue = self.shipment.create_wsdl_object_of_type("Money")
mCustomsValue.Amount = self.invoice_info["Value"]
mCustomsValue.Currency = self.invoice_info["Currency"]
ccd = self.shipment.create_wsdl_object_of_type("CustomsClearanceDetail")
ccd.Commodities = self.mCommodities
ccd.CustomsValue = mCustomsValue
ccd.DutiesPayment = mPayment
self.shipment.RequestedShipment.CustomsClearanceDetail = ccd
# ----------------------------------------------------
# Set ETD (electronic trade documents) settings
def setSpecialServices(self, doc_ids):
# construct objects
ssr = self.shipment.create_wsdl_object_of_type("ShipmentSpecialServicesRequested")
ssr.SpecialServiceTypes.append("ELECTRONIC_TRADE_DOCUMENTS")
ssr.SpecialServiceTypes.append("EVENT_NOTIFICATION")
# set up ETD details
etd = self.shipment.create_wsdl_object_of_type("EtdDetail")
etd.RequestedDocumentCopies = "COMMERCIAL INVOICE"
for i, doc_id in enumerate(doc_ids, start=0):
udrd = self.shipment.create_wsdl_object_of_type("UploadDocumentReferenceDetail")
udrd.DocumentType = "COMMERCIAL_INVOICE" if i == 0 else "OTHER"
udrd.DocumentId = doc_id
udrd.Description = "Commercial_Invoice" if i == 0 else "Product_Description"
udrd.DocumentIdProducer = "CUSTOMER"
ssr.EtdDetail.DocumentReferences.append(udrd)
self.shipment.RequestedShipment.SpecialServicesRequested = ssr
# set Event Notification details
send = self.shipment.create_wsdl_object_of_type("ShipmentEventNotificationDetail")
send.AggregationType = "PER_SHIPMENT"
sens = self.shipment.create_wsdl_object_of_type("ShipmentEventNotificationSpecification")
sens.NotificationDetail.NotificationType = "EMAIL"
sens.NotificationDetail.EmailDetail.EmailAddress = self.shipment.RequestedShipment.Recipient.Contact.EMailAddress
sens.NotificationDetail.EmailDetail.Name = self.shipment.RequestedShipment.Recipient.Contact.PersonName
sens.NotificationDetail.Localization.LanguageCode = "EN"
sens.Role = "SHIPPER"
sens.Events.append("ON_SHIPMENT")
sens.Events.append("ON_EXCEPTION")
sens.Events.append("ON_DELIVERY")
sens.FormatSpecification.Type = "HTML"
send.EventNotifications = sens
self.shipment.RequestedShipment.SpecialServicesRequested.EventNotificationDetail = send
# ----------------------------------------------------
# process the shipment
def processInternationalShipment(self):
from shutil import copyfile
self.shipment.RequestedShipment.ShipTimestamp = datetime.datetime.now().replace(microsecond=0).isoformat()
# print(" ---- **** DETAILS ---- ****")
# print(self.shipment.RequestedShipment)
# print(self.shipment.ClientDetail)
# print(self.shipment.TransactionDetail)
# print("REQUESTED SHIPMENT\n\n", self.shipment.RequestedShipment)
self.shipment.send_request()
# print("RESPONSE\n\n", self.shipment.response)
status = self.shipment.response.HighestSeverity
if status == "SUCCESS" and "CompletedShipmentDetail" in self.shipment.response:
shipment_details = self.shipment.response.CompletedShipmentDetail
package_details = shipment_details.CompletedPackageDetails[0]
tracking_id = package_details.TrackingIds[0].TrackingNumber
email = self.shipment.RequestedShipment.Recipient.Contact.EMailAddress
fedex_cost = "N/A"
if hasattr(package_details, "PackageRating"):
fedex_cost = package_details.PackageRating.PackageRateDetails[0].NetCharge.Amount
# create the shipping PDF label
ascii_label_data = package_details.Label.Parts[0].Image
label_binary_data = binascii.a2b_base64(ascii_label_data)
out_path = self.invoice_info["InvoiceId"] + f"_shipment_label_{tracking_id}.pdf"
out_file = open(out_path, "wb")
out_file.write(label_binary_data)
out_file.close()
# print output information
print(
f"- SUCCESS: Created FedEx label for invoice {self.invoice_info['InvoiceId']}\n tracking ID: {tracking_id}\n email: {email}\n FedEx cost: {fedex_cost}\n Customs value: {self.invoice_info['Value']} {self.invoice_info['Currency']}\n Weight: {self.invoice_info['Weight']}\n output path: {out_path}"
)
# ----------------------------------------------------
# main script
commercial_invoice_path = "commercial_invoice_test.pdf"
product_description_1_path = "product_description_test.pdf"
sender = {
"Company": "Sender Company",
"Name": "Mr Smith",
"Address": ["Address 1", "Address 2"],
"Region": "",
"Zip": "8230",
"City": "Abyhoj",
"Country": "Denmark",
"Phone": "12345678",
"Email": "mail#mail.com",
"CountryCode": "DK",
"Currency": "EUR",
"VAT": "DK12345678",
"Residential": False,
}
recipient = {
"Company": "Recipient Co",
"Name": "Contact Name",
"Address": ["Adr1, Adr2"],
"Region": "MN",
"Zip": "55420",
"City": "Bloomington",
"Country": "United States",
"Phone": "0123456789",
"Email": "mail#mail.com",
"CountryCode": "US",
"Currency": "EUR",
"VAT": "",
"Residential": False,
}
invoice_info = {
"InvoiceId": "14385",
"Weight": 0.11,
"Quantity": 2,
"Value": 20.0,
"Shipping": 25.0,
"ShippingExpress": True,
"Currency": "EUR",
"InvoicePath": commercial_invoice_path,
"Pdfs": [product_description_1_path],
}
# print output
print(f"\n- recipient: {recipient}\n- invoice_info: {invoice_info}\n")
# create FedEx Label Helper and set configuration
flh = FedexLabelHelper()
flh.setShipmentConfig(CONFIG_OBJ=CONFIG_OBJ, invoice_info=invoice_info)
# add sender & recipient info to FedEx shipment
flh.setSenderInfo(sender)
flh.setRecipientInfo(recipient)
# set packaging based on weight
flh.set_packaging_info()
# add reference to CI as only commodity info
flh.add_ci_commodity()
# set duties payment information
flh.setDutiesPaymentInfo()
# upload documents
doc_ids = flh.upload_all_documents()
# link uploaded documents as ETD and setup event notifications
flh.setSpecialServices(doc_ids)
# process shipments and create shipping labels
flh.processInternationalShipment()
I get this error when I run the script and I cannot see the solution. This program is supposed to draw a giveaway from a sqlite3 file which has the number of raffle tickets for a user. And recently the program the gives that creates the sqlite3 file updated some stuff (The script is made by me) and I can figure out the solution.
Traceback (most recent call last):
File "C:\Users\Admin\Desktop\Draw\Test\dave-draw.py", line 244, in <module>
dd = DaveDraw()
File "C:\Users\Admin\Desktop\Draw\Test\dave-draw.py", line 64, in __init__
self.get_viewers()
File "C:\Users\Admin\Desktop\Draw\Test\dave-draw.py", line 215, in
get_viewers
''').fetchall()
sqlite3.OperationalError: no such column: viewer_id
there's the code
#!/usr/bin/env python3
import pdb
import random
import sqlite3
class Viewer(object):
def __init__(self,
viewer_id,
twitch_name,
beam_name,
beam_id,
viewer_type,
rank,
points,
points2,
hours,
raids,
gains_currency,
gains_hours,
in_giveaways,
last_seen,
sub,
entrance_message,
entrance_message_type,
entrance_sfx
):
self.viewer_id = viewer_id
self.twitch_name = twitch_name
self.beam_name = beam_name
self.beam_id = beam_id
self.viewer_type = viewer_type
self.rank = rank
self.points = points
self.points2 = points2
self.hours = hours
self.raids = raids
self.gains_currency = gains_currency
self.gains_hours = gains_hours
self.in_giveaways = in_giveaways
self.last_seen = last_seen
self.sub = sub
self.entrance_message = entrance_message
self.entrance_message_type = entrance_message_type
self.entrance_sfx = entrance_sfx
def win_chance(self, total_tickets):
"""
Takes the total tickets (points) as a paramter and works
out the percentage chance that the viewer has of winning.
Returns the viewers win chance in percent.
"""
percent = total_tickets / 100.00
return self.points2 / percent
class DaveDraw(object):
def __init__(self):
self.debug = False
self.database_path = 'Viewers3DB.sqlite'
self.db_conn = sqlite3.connect(self.database_path)
self.get_viewers()
self.calculate_total_points()
self.assign_tickets()
def assign_tickets(self):
"""
Assigns each user a number range based on the number of
tickets they have.
e.g.
10 1-10
10 11-20
30 21-50
1 51
"""
self.tickets = {}
latest_ticket = 0
for viewer in self.viewers:
# skip anyone with no points
if viewer.points2 == 0:
continue
ticket_range_beg = latest_ticket + 1
ticket_range_end = latest_ticket + 1 + viewer.points2
latest_ticket = ticket_range_end
viewer.tickets = range(ticket_range_beg, ticket_range_end)
# assign a range of tickets:
if self.debug:
print("Assigning viewer twitch: %s beam: %s tickets %i-%i" % (viewer.twitch_name, viewer.beam_name, viewer.tickets.start, viewer.tickets.stop))
if ticket_range_beg == ticket_range_end:
if self.debug:
print("Assigning ticket {} to {}".format(ticket_range_beg, viewer.twitch_name))
self.tickets[ticket_range_beg] = viewer
next
for ticket in viewer.tickets:
if self.debug:
print("Assigning ticket {} to {}".format(ticket, viewer.twitch_name))
self.tickets[ticket] = viewer
def calculate_total_points(self):
"""
Gets the total amount of points awarded to all
viewers.
"""
self.total_points = 0
for viewer in self.viewers:
self.total_points += viewer.points2
self.total_points_percent = self.total_points / 100
print("Total points awarded (total tickets): %s" % self.total_points)
def draw(self):
"""
Picks a random number between 1 and total tickets, finds
the user that has been assigned tickets within that range and
returns the user.
"""
ticket = random.randint(1, self.total_points)
try:
winner = self.tickets[ticket]
except:
pdb.set_trace()
print("\n===== WINNER Twitch: {} / Beam: {} =====\n".format(winner.twitch_name, winner.beam_id))
print("Picked ticket {}\n".format(ticket))
print("Winner win chance: {:f}".format(winner.win_chance(self.total_points)))
print("Winner's ticket range: {}-{}".format(winner.tickets.start, winner.tickets.stop))
print("Winner's ticket amount: {}\n".format(winner.points2))
self.display_viewer(winner)
def display_random_viewer(self):
"""
Displays random viewer.
"""
self.display_viewer(self.get_random_viewer())
def display_viewer(self, viewer):
"""
Outputs the data on all viewers.
"""
print("""Viewer ID: %s\nTwitch Name: %s\nBeam Name: %s\nBeam ID: %s\nRank: %s\nPoints: %s\nPoints2: %s\nHours: %s\nRaids: %s\nGains Currency: %s\nGains Hours: %s\nInGiveaways: %s\nLastSeen: %s\nEntrance Message: %s\nEntranceMsgType: %s\nEntranceSFX: %s"""
% (
viewer.viewer_id,
viewer.twitch_name,
viewer.beam_name,
viewer.beam_id,
viewer.rank,
viewer.points,
viewer.points2,
viewer.hours,
viewer.raids,
viewer.gains_currency,
viewer.gains_hours,
viewer.in_giveaways,
viewer.last_seen,
viewer.entrance_message,
viewer.entrance_message_type,
viewer.entrance_sfx
)
)
def get_random_viewer(self):
"""
Gets a completely random viewer.
"""
return random.choice(self.viewers)
def get_viewers(self):
"""
Gets data on all the viewers in the database and stores
the data in self.viewers.
"""
c = self.db_conn.cursor()
viewers = c.execute('''
SELECT
viewer_id,
TwitchName,
BeamName,
BeamID,
Type,
Rank,
Points,
Points2,
Hours,
Raids,
GainsCurrency,
GainsHours,
InGiveaways,
LastSeen,
Sub,
EntranceMessage,
EntranceMsgType,
EntranceSFX
FROM Viewer
WHERE Type != 1
AND TwitchName NOT IN (
\'treeboydave\',
\'treebotdave\'
);
''').fetchall()
self.viewers = []
for cur_viewer in viewers:
self.viewers.append(
Viewer(
cur_viewer[0],
cur_viewer[1],
cur_viewer[2],
cur_viewer[3],
cur_viewer[4],
cur_viewer[5],
cur_viewer[6],
cur_viewer[7],
cur_viewer[8],
cur_viewer[9],
cur_viewer[10],
cur_viewer[11],
cur_viewer[12],
cur_viewer[13],
cur_viewer[14],
cur_viewer[15],
cur_viewer[16],
cur_viewer[17]
)
)
if __name__ == '__main__':
dd = DaveDraw()
dd.draw()
All your other SQL columns are capitalised, any chance that's why it's not finding the viewer_id column? Maybe it's Viewer_Id or similar?
If you sql execute 'HELP TABLE Viewer' and print what it returns, it will give you an outline of all of the columns in that database table, so you can make sure you have the capitalisation correct, or whether the column actually isn't there at all.
I really enjoyed the graph traversals of arangodb which allows me to visit any path or nodes with little query sweats. However, i m stacked with a context which is already implemented in neo4j, I believe anyone using arangodb might find this useful for his future operation.
I have successfully imported the list of product categories google product taxonomy into arangodb database. in a vertex collection named taxonomy and edge collection named catof.
If i m correct, from this query, i m able to fetch all vertices and linked edges.
FOR t IN taxonomy
for c in inbound t catof
sort c.name asc
return {c}
While feeding the taxonomy documents, parent vertex do not have an edge if any of both parts _from, _to are null. i need to mention, i m using flask-script and python-arango to proceed on these operations, they have been helpful.
manager = Manager(app)
tax_item = storegraph.vertex_collection('taxonomy')
catof = storegraph.edge_collection('catof')
#manager.command
def fetch_tree():
dictionary = {}
with open('input.csv') as file:
for row in file.readlines():
things = row.strip().split(' > ')
dictionary[things[0]] = None
i, j = 0, 1
while j < len(things):
parent, child = things[i], things[j]
dictionary[child] = parent
i += 1
j += 1
# for key in dictionary:
#tax_item.insert({"name": key})
for child, parent in dictionary.iteritems():
# edge_collection.insert_edge({from: vertex_collection /
# parent, to: vertex_collection / child})
chl, par = tax_item.find({'name': child}),
tax_item.find({'name': parent})
c, p = [h for h in chl], [a for a in par]
if c and p:
#print 'Child: %s parent: %s' % (c[0]['_id'], p[0]['_id'])
catof.insert({'_from': c[0]['_id'], '_to': p[0]['_id'] })
#print '\n'
After operation, i have the following sample vertices.
[{"_key": "5246198", "_id": "taxonomy/5246198","name": "Computers"},
{"_key": "5252911", "_id": "taxonomy/5252911","name": "Hardwares"},
{"_key": "5257587", "_id": "taxonomy/5257587", "name": "Hard disk"
}]
and edges
[
{ "_key": "5269883", "_id": "catof/5269883", "_from": "taxonomy/5246198", "_to": "taxonomy/5252911"},
{"_key": "5279833", "_id": "catof/5279833", "_from": "taxonomy/5252911",
"_to": "taxonomy/5257587"}]
Now my question is:
How do I fetch only parent documents? i.e Computers
From parent documents, how do i print all their children using ? to be a format of Computers, Hardwares, Hard Disks