Having an issue where the end main.exe file can be booted, however when I try and access one of the files inside the "examples" folder, it cannot find it. My file structure can be found here: https://github.com/Zach10a/PteraSoftware/tree/create_gui
My .spec file can also be found there, but is as follows
# -*- mode: python ; coding: utf-8 -*-
import os
import sys
import PySide2
from PyInstaller.building.api import PYZ, EXE, COLLECT
from PyInstaller.building.build_main import Analysis
block_cipher = None
one_dir_mode = True
binaries = []
if sys.platform.startswith('win'):
qt_plugins_path = os.path.join(PySide2.__path__[0], "plugins")
binaries = [
(os.path.join(PySide2.__path__[0], "plugins"), 'PySide2')
]
elif sys.platform.startswith('linux'):
qt_plugins_path = os.path.join(PySide2.__path__[0], "Qt", "plugins", "platforms")
binaries = [
(os.path.join(sys.base_prefix, "lib", "libspatialindex_c.so"), '.'),
# (os.path.join(PySide2.__path__[0], "Qt", "plugins", "platforms"), '.')
]
upx = False # UPX does not play with anything Qt
upx_exclude = [
'PySide2',
'qwindows.dll'
]
a = Analysis(
['main.py'],
pathex=[],
binaries=[],
datas=[('docs/Logo.ico', 'docs'),
('docs/Black_Text_Logo.ico', 'docs'),
('docs/Logo.png', 'docs'),
('docs/Black_Text_Logo.png', 'docs'),
("README.md", '.')
# ('examples/analyze_steady_trim_example.py', 'examples'),
# ('examples/analyze_unsteady_trim_example.py', 'examples'),
# ('examples/steady_convergence_example.py', 'examples'),
# ('examples/steady_horseshoe_vortex_lattice_method_solver.py', 'examples'),
# ('examples/steady_ring_vortex_lattice_method_solver.py', 'examples'),
# ('examples/unsteady_ring_vortex_lattice_method_solver_static.py', 'examples'),
# ('examples/unsteady_ring_vortex_lattice_method_solver_variable.py', 'examples'),
# ('examples/unsteady_ring_vortex_lattice_method_solver_variable_formation.py', 'examples'),
# ('examples/unsteady_static_convergence_example.py', 'examples'),
# ('examples/unsteady_variable_convergence_example.py', 'examples'),
],
hiddenimports=['vtkmodules','vtkmodules.all','vtkmodules.qt.QVTKRenderWindowInteractor','vtkmodules.util','vtkmodules.util.numpy_support', 'examples'],
hookspath=[],
hooksconfig={},
runtime_hooks=[],
excludes=[],
win_no_prefer_redirects=False,
win_private_assemblies=False,
cipher=block_cipher,
noarchive=False,
)
pyz = PYZ(a.pure, a.zipped_data, cipher=block_cipher)
exe = EXE(
pyz,
a.scripts,
[],
exclude_binaries=True,
name='main',
debug=False,
bootloader_ignore_signals=False,
strip=False,
upx=True,
console=True,
disable_windowed_traceback=False,
argv_emulation=False,
target_arch=None,
codesign_identity=None,
entitlements_file=None,
icon='docs/Logo.ico'
)
coll = COLLECT(
exe,
a.binaries,
a.zipfiles,
a.datas,
strip=False,
upx=True,
upx_exclude=[],
name='main',
)
I get the follwing Traceback and error message:
Builtin modules imported
QTCore imported
QtGUI imported
Traceback (most recent call last):
File "main.py", line 29, in <lambda>
File "main.py", line 42, in exampleMenu
FileNotFoundError: [WinError 3] The system cannot find the path specified: 'examples'
I've tried adding them all in as datas in the analysis section (as you can see below, they are blanked out so I can get the error message), however that's not exactly scalable and feels very sloppy. I think it is something to do with using importlib.import_module(file) in main.py to import those example files as modules.
Related
I am trying to create a dag for a ETL solution where we have 4 stages to the the pipeline. We have source_2_s3,staging,dim_population,fact_loads
Each of these stages have multiple glue jobs in them that can run in parallel. I am trying to run these stages as taskgroups and passing a list of jobnames as parameters so we can create the glue operators on runtime but I am only getting one gluejob for each task group? What am I doing wrong. My code is as follows:
The yaml file contains all jobs for each task group and the gluejob script location as keyvalue pair
from os import path
from airflow import DAG
from airflow.providers.amazon.aws.operators.glue import AwsGlueJobOperator
import yaml
from airflow.models import Variable
from airflow.utils.dates import days_ago
from airflow.operators.dummy import DummyOperator
from airflow.utils.task_group import TaskGroup
AwsGlueJobOperator.ui_color = "#F3D5C5"
DAG_FOLDER_PATH = path.dirname(__file__)
ENVIRONMENT = Variable.get("environment")
CONFIG_FILE_NAME = f"dwh_config_{ENVIRONMENT}.yml"
with open(path.join(DAG_FOLDER_PATH, CONFIG_FILE_NAME), 'r') as fl:
cfg = yaml.safe_load(fl)["dwh"]
aws_conn_id = cfg["aws"]["aws_conn_id"]
glue_scripts_bucket_name = cfg["glue"]["app"]["bucket_name"]
src1_tg = cfg["glue"]["app"]["src1_taskgroup"]
src2_tg = cfg["glue"]["app"]["src2_taskgroup"]
staging_tg = cfg["glue"]["app"]["staging_taskgroup"]
dim_tg = cfg["glue"]["app"]["dim_taskgroup"]
fact_tg = cfg["glue"]["app"]["fact_taskgroup"]
def glue_operator(list_of_jobs):
for jobname, script_path in list_of_jobs.items():
return AwsGlueJobOperator(
task_id=jobname,
dag=dag,
aws_conn_id='aws_default',
region_name='eu-west-2',
job_name=jobname,
script_location=path.join("s3://", glue_scripts_bucket_name,
script_path)
)
with DAG(dag_id="CLIENTUSAGE_DAILY_DWH_REFRESH", schedule_interval="#daily", start_date=days_ago(1),
tags=['Clientusage']) as dag:
batch_start_job = DummyOperator(task_id="START")
batch_close_job = DummyOperator(task_id="END")
with TaskGroup(group_id='src1_tg ') as src1_taskgroup:
list = glue_operator(src1_tg)
with TaskGroup(group_id='src2_tg') as src2_taskgroup:
list = glue_operator(src2_tg)
with TaskGroup(group_id='staging_tg') as staging_taskgroup:
list = glue_operator(staging_tg)
with TaskGroup(group_id='dim_tg') as dim_taskgroup:
list = glue_operator(dim_tg)
with TaskGroup(group_id='fact_tg') as fact_taskgroup:
list = glue_operator(fact_tg)
batch_start_job >> [src1_taskgroup,
src2_taskgroup] >> staging_taskgroup >> dim_taskgroup >> fact_taskgroup
'''
The issue was my function for generating dags. I forgot the basics of functions :D. Had to append all operators to an array before returning it.
def glue_operator(list_of_jobs):
operators = []
for jobname, script_path in list_of_jobs.items():
operators.append(AwsGlueJobOperator(
task_id=jobname,
dag=dag,
aws_conn_id='aws_default',
region_name='eu-west-2',
job_name=jobname,
script_location=path.join("s3://", glue_scripts_bucket_name,
script_path)
))
return operators
I need to download multiple 10-ks documents, however, this code works fine if i download the 10-ks between 5-10 companies. But if i increase the number of companies in [cik_lookup function]. Here's code.
import nltk
import numpy as np
import pandas as pd
import pickle
import pprint
import project_helper
from tqdm import tqdm
Here's the py file that includes project_helper functions.
import matplotlib.pyplot as plt
import requests
from ratelimit import limits, sleep_and_retry
class SecAPI(object):
SEC_CALL_LIMIT = {'calls': 10, 'seconds': 1}
#staticmethod
#sleep_and_retry
# Dividing the call limit by half to avoid coming close to the limit
#limits(calls=SEC_CALL_LIMIT['calls'] / 2, period=SEC_CALL_LIMIT['seconds'])
def _call_sec(url):
return requests.get(url)
def get(self, url):
return self._call_sec(url).text
def print_ten_k_data(ten_k_data, fields, field_length_limit=50):
indentation = ' '
print('[')
for ten_k in ten_k_data:
print_statement = '{}{{'.format(indentation)
for field in fields:
value = str(ten_k[field])
# Show return lines in output
if isinstance(value, str):
value_str = '\'{}\''.format(value.replace('\n', '\\n'))
else:
value_str = str(value)
# Cut off the string if it gets too long
if len(value_str) > field_length_limit:
value_str = value_str[:field_length_limit] + '...'
print_statement += '\n{}{}: {}'.format(indentation * 2, field, value_str)
print_statement += '},'
print(print_statement)
print(']')
The first step it to download NLP Corpora.
nltk.download('stopwords')
nltk.download('wordnet')
Than Get 10ks
#cik_lookup = {
# 'GOOGL':'0001288776',
# 'AAPL':'0000320193',
# 'FACEBOOK':'0001326801',
# 'AMZN':'0001018724',
# 'MSFT':'0000789019'}
cik_lookup = {
'AEP': '0000004904',
'AXP': '0000004962',
'BA': '0000012927',
'BK': '0001390777',
'CAT': '0000018230',
'DE': '0000315189',
'DIS': '0001001039',
'DTE': '0000936340',
'ED': '0001047862',
'EMR': '0000032604',
'ETN': '0001551182',
'GE': '0000040545',
'IBM': '0000051143',
'IP': '0000051434',
'JNJ': '0000200406',
'KO': '0000021344',
'LLY': '0000059478',
'MCD': '0000063908',
'MO': '0000764180',
'MRK': '0000310158',
'MRO': '0000101778',
'PCG': '0001004980',
'PEP': '0000077476',
'PFE': '0000078003',
'PG': '0000080424',
'PNR': '0000077360',
'SYY': '0000096021',
'TXN': '0000097476',
'UTX': '0000101829',
'WFC': '0000072971',
'WMT': '0000104169',
'WY': '0000106535',
'XOM': '0000034088'}
Get list of 10-ks
sec_api = project_helper.SecAPI()
from bs4 import BeautifulSoup
def get_sec_data(cik, doc_type, start=0, count=60):
newest_pricing_data = pd.to_datetime('2021-01-01')
rss_url = 'https://www.sec.gov/cgi-bin/browse-edgar?action=getcompany' \
'&CIK={}&type={}&start={}&count={}&owner=exclude&output=atom' \
.format(cik, doc_type, start, count)
sec_data = sec_api.get(rss_url)
feed = BeautifulSoup(sec_data.encode('utf-8'), 'xml').feed
entries = [
(
entry.content.find('filing-href').getText(),
entry.content.find('filing-type').getText(),
entry.content.find('filing-date').getText())
for entry in feed.find_all('entry', recursive=False)
if pd.to_datetime(entry.content.find('filing-date').getText()) <= newest_pricing_data]
return entries
example_ticker = 'AEP'
sec_data = {}
for ticker, cik in cik_lookup.items():
sec_data[ticker] = get_sec_data(cik, '10-K')
The code works fine if i download the 10-ks between 5-10 companies. But if i increase the number of companies in [cik_lookup function] I get the following error. The first error I got is as below.
UnicodeEncodeError Traceback (most recent call last)
<ipython-input-8-28a784054794> in <module>()
20
21 for ticker, cik in cik_lookup.items():
---> 22 sec_data[ticker] = get_sec_data(cik, '10-K')
<ipython-input-8-28a784054794> in get_sec_data(cik, doc_type, start, count)
5 rss_url = 'https://www.sec.gov/cgi-bin/browse-edgar?action=getcompany' '&CIK={}&type={}&start={}&count={}&owner=exclude&output=atom' .format(cik, doc_type, start, count)
6 sec_data = sec_api.get(rss_url)
----> 7 feed = BeautifulSoup(sec_data.encode('ascii'), 'xml').feed
8 entries = [
9 (
UnicodeEncodeError: 'ascii' codec can't encode characters in position 2599-2601: ordinal not in range(128)
However, after some google search over BeutifulSoup(ecodes) I changed it to utf-8 and then got the following error.
---------------------------------------------------------------------------
AttributeError Traceback (most recent call last)
<ipython-input-9-9c77ed07af2d> in <module>()
20
21 for ticker, cik in cik_lookup.items():
---> 22 sec_data[ticker] = get_sec_data(cik, '10-K')
<ipython-input-9-9c77ed07af2d> in get_sec_data(cik, doc_type, start, count)
11 entry.content.find('filing-type').getText(),
12 entry.content.find('filing-date').getText())
---> 13 for entry in feed.find_all('entry', recursive=False)
14 if pd.to_datetime(entry.content.find('filing-date').getText()) <= newest_pricing_data]
15
AttributeError: 'NoneType' object has no attribute 'find_all'
The project can be accessed here at the following github repo.
github repo herealso.
When I run the string below in my command line, it works fine. But when I run it from R, it does not.
I run this:
>cmd <- "python -c 'import sys; import pandas; import scrublet; df = pandas.read_csv(\"C:\\Users\\User\\AppData\\Local\\Temp\\RtmpOmMtOp\\file383068ca4fa\"); scrub = scrublet.Scrublet(df); doublet_scores, predicted_doublets = scrub.scrub_doublets(); pandas.DataFrame(doublet_scores).to_csv(\"C:\\Users\\User\\AppData\\Local\\Temp\\RtmpOmMtOp\\file383068ca4fa.doubletScores\");'"
tmp <- system(cmd, intern=T)
Warning message:
In system(cmd, intern = T) :
running command 'python -c 'import sys; import pandas; import scrublet; df = pandas.read_csv("C:\Users\User\AppData\Local\Temp\RtmpOmMtOp\file383068ca4fa"); scrub = scrublet.Scrublet(df); doublet_scores, predicted_doublets = scrub.scrub_doublets(); pandas.DataFrame(doublet_scores).to_csv("C:\Users\User\AppData\Local\Temp\RtmpOmMtOp\file383068ca4fa.doubletScores");'' had status 1
I have a program that I want to distribute to several customers but with their own name and logo and with different modes. Each customer need 3 different files and if I have 20 customers I would need 60 spec files. I have tried to create a .spec file that would create all in 1 compile but it just overwrites the same file and I end up with 1 file.
Is it possible to create multiple executables with PyInstaller from a single .py using only 1 .spec file?
I tried creating a list with all EXE, PYZ and so on but still only 1 executable gets created. In the 'build' folder created after i can see multiple .toc .pyz .pkg with different names. 00,01,02 and so on. It seems it is possible to do this but I'm missing something.
What am I doing wrong?
I'm using Python 3.6 and PyInstaller 3.5.
# -*- mode: python -*-
import glob
import os
import sys
block_cipher = None
companies_to_create = ["CustomerA", "CustomerB"]
modes = ["config", "service"]
# Testing list, static
list_PYZ = [None] * 4
list_EXE = [None] * 4
list_A = [None] * 4
app_nr = 0
for company in companies_to_create:
for mode in modes:
# Changes mode in file to create
with open("mainprogram/mode.py", "w") as f_mode:
f_mode.write('mode="' + mode + '"')
f_mode.close()
# Changes company in file to create
with open("mainprogram/company.py", "w") as f_company:
f_company.write('company="' + company + '"')
f_company.close()
from PyInstaller.utils.hooks import collect_submodules, collect_data_files
from mainprogram.brands import company_app
hiddenimports = collect_submodules('pubsub')
list_A[app_nr] = Analysis(['mainprogram/mainprogram.py'],
pathex=[],
binaries=[],
hiddenimports=hiddenimports,
hookspath=[],
runtime_hooks=[],
excludes=['tkinter'],
win_no_prefer_redirects=False,
win_private_assemblies=False,
cipher=block_cipher)
images = glob.glob("mainprogram/images/**/*", recursive=True)
icons = glob.glob("mainprogram/icons/**/*", recursive=True)
files = images + icons
for f in files:
if os.path.isfile(f):
path = f.split('mainprogram/')[1]
list_A[app_nr].datas += [((path, f, 'Data'))]
list_PYZ[app_nr] = PYZ(list_A[app_nr].pure, list_A[app_nr].zipped_data, cipher=block_cipher)
list_EXE[app_nr] = EXE(list_PYZ[app_nr],
list_A[app_nr].scripts,
list_A[app_nr].binaries,
list_A[app_nr].zipfiles,
list_A[app_nr].datas,
name=company_app.exe_name,
debug=False,
strip=False,
upx=False,
console=False,
icon='mainprogram/icons/' + company + '.ico')
app_nr += 1
I use the package keras under R and I would like to know if there was a command like python with plot_model () which allows to display its neuron network
library(keras)
for example I would like to display this neural network under R
model <- keras_model_sequential()
model %>%
layer_dense(units = 5, input_shape = 2) %>%
layer_activation("relu") %>%
layer_dense(units = 1)
I install package kerasR for use the function plot_model(), but i have this error.
> library(kerasR)
> plot_model(model)
Error in py_call_impl(callable, dots$args, dots$keywords) :
ImportError: Failed to import pydot. You must install pydot and graphviz for `pydotprint` to work.
Detailed traceback:
File "C:\Users\Idriss\ANACON~1\envs\R-TENS~1\lib\site-packages\keras\utils\vis_utils.py", line 131, in plot_model
dot = model_to_dot(model, show_shapes, show_layer_names, rankdir)
File "C:\Users\Idriss\ANACON~1\envs\R-TENS~1\lib\site-packages\keras\utils\vis_utils.py", line 52, in model_to_dot
_check_pydot()
File "C:\Users\Idriss\ANACON~1\envs\R-TENS~1\lib\site-packages\keras\utils\vis_utils.py", line 27, in _check_pydot
raise ImportError('Failed to import pydot. You must install pydot'
I'm use windows 10 64 bits, i use RStudio with Anaconda
In [4] pydot.Dot.create(pydot.Dot())
Out[4]: b"%!PS-Adobe-3.0\r\n%%Creator: graphviz version 2.38.0 (20140413.2041)\r\n%%Title: G\r\n%%Pages: (atend)\r\n%%BoundingBox: (atend)\r\n%%EndComments\r\nsave\r\n%%BeginProlog\r\n/DotDict 200 dict def\r\nDotDict begin\r\n\r\n/setupLatin1 {\r\nmark\r\n/EncodingVector 256 array def\r\n EncodingVector 0\r\n\r\nISOLatin1Encoding 0 255 getinterval putinterval\r\nEncodingVector 45 /hyphen put\r\n\r\n% Set up ISO Latin 1 character encoding\r\n/starnetISO {\r\n dup dup findfont dup length dict begin\r\n { 1 index /FID ne { def }{ pop pop } ifelse\r\n } forall\r\n /Encoding EncodingVector def\r\n currentdict end definefont\r\n} def\r\n/Times-Roman starnetISO def\r\n/Times-Italic starnetISO def\r\n/Times-Bold starnetISO def\r\n/Times-BoldItalic starnetISO def\r\n/Helvetica starnetISO def\r\n/Helvetica-Oblique starnetISO def\r\n/Helvetica-Bold starnetISO def\r\n/Helvetica-BoldOblique starnetISO def\r\n/Courier starnetISO def\r\n/Courier-Oblique starnetISO def\r\n/Courier-Bold starnetISO def\r\n/Courier-BoldOblique starnetISO def\r\ncleartomark\r\n} bind def\r\n\r\n%%BeginResource: procset graphviz 0 0\r\n/coord-font-family /Times-Roman def\r\n/default-font-family /Times-Roman def\r\n/coordfont coord-font-family findfont 8 scalefont def\r\n\r\n/InvScaleFactor 1.0 def\r\n/set_scale {\r\n dup 1 exch div /InvScaleFactor exch def\r\n scale\r\n} bind def\r\n\r\n% styles\r\n/solid { [] 0 setdash } bind def\r\n/dashed { [9 InvScaleFactor mul dup ] 0 setdash } bind def\r\n/dotted { [1 InvScaleFactor mul 6 InvScaleFactor mul] 0 setdash } bind def\r\n/invis {/fill {newpath} def /stroke {newpath} def /show {pop newpath} def} bind def\r\n/bold { 2 setlinewidth } bind def\r\n/filled { } bind def\r\n/unfilled { } bind def\r\n/rounded { } bind def\r\n/diagonals { } bind def\r\n/tapered { } bind def\r\n\r\n% hooks for setting color \r\n/nodecolor { sethsbcolor } bind def\r\n/edgecolor { sethsbcolor } bind def\r\n/graphcolor { sethsbcolor } bind def\r\n/nopcolor {pop pop pop} bind def\r\n\r\n/beginpage {\t% i j npages\r\n\t/npages exch def\r\n\t/j exch def\r\n\t/i exch def\r\n\t/str 10 string def\r\n\tnpages 1 gt {\r\n\t\tgsave\r\n\t\t\tcoordfont setfont\r\n\t\t\t0 0 moveto\r\n\t\t\t(\\() show i str cvs show (,) show j str cvs show (\\)) show\r\n\t\tgrestore\r\n\t} if\r\n} bind def\r\n\r\n/set_font {\r\n\tfindfont exch\r\n\tscalefont setfont\r\n} def\r\n\r\n% draw text fitted to its expected width\r\n/alignedtext {\t\t\t% width text\r\n\t/text exch def\r\n\t/width exch def\r\n\tgsave\r\n\t\twidth 0 gt {\r\n\t\t\t[] 0 setdash\r\n\t\t\ttext stringwidth pop width exch sub text length div 0 text ashow\r\n\t\t} if\r\n\tgrestore\r\n} def\r\n\r\n/boxprim {\t\t\t\t% xcorner ycorner xsize ysize\r\n\t\t4 2 roll\r\n\t\tmoveto\r\n\t\t2 copy\r\n\t\texch 0 rlineto\r\n\t\t0 exch rlineto\r\n\t\tpop neg 0 rlineto\r\n\t\tclosepath\r\n} bind def\r\n\r\n/ellipse_path {\r\n\t/ry exch def\r\n\t/rx exch def\r\n\t/y exch def\r\n\t/x exch def\r\n\tmatrix currentmatrix\r\n\tnewpath\r\n\tx y translate\r\n\trx ry scale\r\n\t0 0 1 0 360 arc\r\n\tsetmatrix\r\n} bind def\r\n\r\n/endpage { showpage } bind def\r\n/showpage { } def\r\n\r\n/layercolorseq\r\n\t[\t% layer color sequence - darkest to lightest\r\n\t\t[0 0 0]\r\n\t\t[.2 .8 .8]\r\n\t\t[.4 .8 .8]\r\n\t\t[.6 .8 .8]\r\n\t\t[.8 .8 .8]\r\n\t]\r\ndef\r\n\r\n/layerlen layercolorseq length def\r\n\r\n/setlayer {/maxlayer exch def /curlayer exch def\r\n\tlayercolorseq curlayer 1 sub layerlen mod get\r\n\taload pop sethsbcolor\r\n\t/nodecolor {nopcolor} def\r\n\t/edgecolor {nopcolor} def\r\n\t/graphcolor {nopcolor} def\r\n} bind def\r\n\r\n/onlayer { curlayer ne {invis} if } def\r\n\r\n/onlayers {\r\n\t/myupper exch def\r\n\t/mylower exch def\r\n\tcurlayer mylower lt\r\n\tcurlayer myupper gt\r\n\tor\r\n\t{invis} if\r\n} def\r\n\r\n/curlayer 0 def\r\n\r\n%%EndResource\r\n%%EndProlog\r\n%%BeginSetup\r\n14 default-font-family set_font\r\n1 setmiterlimit\r\n% /arrowlength 10 def\r\n% /arrowwidth 5 def\r\n\r\n% make sure pdfmark is harmless for PS-interpreters other than Distiller\r\n/pdfmark where {pop} {userdict /pdfmark /cleartomark load put} ifelse\r\n% make '<<' and '>>' safe on PS Level 1 devices\r\n/languagelevel where {pop languagelevel}{1} ifelse\r\n2 lt {\r\n userdict (<<) cvn ([) cvn load put\r\n userdict (>>) cvn ([) cvn load put\r\n} if\r\n\r\n%%EndSetup\r\nsetupLatin1\r\n%%Page: 1 1\r\n%%PageBoundingBox: 36 36 44 44\r\n%%PageOrientation: Portrait\r\n0 0 1 beginpage\r\ngsave\r\n36 36 8 8 boxprim clip newpath\r\n1 1 set_scale 0 rotate 40 40 translate\r\nendpage\r\nshowpage\r\ngrestore\r\n%%PageTrailer\r\n%%EndPage: 1\r\n%%Trailer\r\n%%Pages: 1\r\n%%BoundingBox: 36 36 44 44\r\nend\r\nrestore\r\n%%EOF\r\n"
First thing first, the error:
File "C:\Users\Idriss\ANACON~1\envs\R-TENS~1\lib\site-packages\keras\utils\vis_utils.py", line 52, in model_to_dot
_check_pydot()
If we check the file C:\Users\Idriss\ANACON~1\envs\R-TENS~1\lib\site-packages\keras\utils\vis_utils.py and search for the function _check_pydot():
def _check_pydot():
try:
# Attempt to create an image of a blank graph
# to check the pydot/graphviz installation.
pydot.Dot.create(pydot.Dot())
except Exception:
# pydot raises a generic Exception here,
# so no specific class can be caught.
raise ImportError('Failed to import pydot. You must install pydot'
' and graphviz for `pydotprint` to work.')
This error message is lack of information since it catch ALL exception instead of specific execption and raise hard-coded error ImportError(Failed to import blah blah).
To ensure it import the relevant pydot, we should also check import part in that file (Rerun R and library(kerasR) to test):
import os
print("hole 0")
try:
# pydot-ng is a fork of pydot that is better maintained.
import pydot_ng as pydot
print("hole 1")
except ImportError:
# pydotplus is an improved version of pydot
try:
print("hole 1.2")
import pydotplus as pydot
print("hole 2")
except ImportError:
# Fall back on pydot if necessary.
try:
print("hole 3")
import pydot
except ImportError:
print("hole 4")
pydot = None
print("hole -1: " + str(locals())) #alternative way to debug
...
Tips: The safer way to debug is userepr instead of str.
If you manually run python in interactive mode and do pydot.Dot.create(pydot.Dot()), you will find out the exact exception (below is my Linux sample):
xb#dnxb:~/anaconda3/envs/r-tensorflow/bin$ ./python
Python 3.6.3 |Anaconda, Inc.| (default, Nov 20 2017, 20:41:42)
[GCC 7.2.0] on linux
Type "help", "copyright", "credits" or "license" for more information.
>>> import pydot
>>> pydot.Dot()
<pydot.Dot object at 0x7f7d045cdb38>
>>> pydot.Dot
<class 'pydot.Dot'>
>>> pydot.Dot.create(pydot.Dot())
Traceback (most recent call last):
File "/home/xiaobai/anaconda3/envs/r-tensorflow/lib/python3.6/site-packages/pydot.py", line 1878, in create
stderr=subprocess.PIPE, stdout=subprocess.PIPE)
File "/home/xiaobai/anaconda3/envs/r-tensorflow/lib/python3.6/subprocess.py", line 709, in __init__
restore_signals, start_new_session)
File "/home/xiaobai/anaconda3/envs/r-tensorflow/lib/python3.6/subprocess.py", line 1344, in _execute_child
raise child_exception_type(errno_num, err_msg, err_filename)
FileNotFoundError: [Errno 2] No such file or directory: 'dot': 'dot'
During handling of the above exception, another exception occurred:
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
File "/home/xiaobai/anaconda3/envs/r-tensorflow/lib/python3.6/site-packages/pydot.py", line 1883, in create
prog=prog))
Exception: "dot" not found in path.
>>>
Let's print some variables used in the file /home/xiaobai/anaconda3/envs/r-tensorflow/lib/python3.6/site-packages/pydot.py before the line 1878:
try:
print("env: " + str(env))
print("cmdline: " + str(cmdline))
print("tmp_dir: " + str(tmp_dir))
p = subprocess.Popen(
cmdline,
env=env,
cwd=tmp_dir,
shell=False,
stderr=subprocess.PIPE, stdout=subprocess.PIPE)
except OSError as e:
if e.errno == os.errno.ENOENT:
raise Exception(
'"{prog}" not found in path.'.format(
prog=prog))
else:
raise
Restart your python interpreter, rerun the import pydot and pydot.Dot.create(pydot.Dot()), it will shows:
xb#dnxb:~/anaconda3/envs/r-tensorflow/bin$ ./python
Python 3.6.3 |Anaconda, Inc.| (default, Nov 20 2017, 20:41:42)
[GCC 7.2.0] on linux
Type "help", "copyright", "credits" or "license" for more information.
>>> import pydot
>>> pydot.Dot.create(pydot.Dot())
env: {'PATH': '/home/xiaobai/anaconda3/bin:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:...<My other PATH>'}
cmdline: ['dot', '-Tps', '/tmp/tmpffo17gx5']
tmp_dir: /tmp
Traceback (most recent call last):
File "/home/xiaobai/anaconda3/envs/r-tensorflow/lib/python3.6/site-packages/pydot.py", line 1881, in create
stderr=subprocess.PIPE, stdout=subprocess.PIPE)
So basically what it does is run the command dot -Tps /tmp/tmpffo17gx5 but failed due to dot command not found.
In Linux, it will suggest run sudo apt install graphviz to install dot if I run the command manually in terminal:
xb#dnxb:~/anaconda3/envs/r-tensorflow/bin$ dot
The program 'dot' is currently not installed. You can install it by typing:
sudo apt install graphviz
xb#dnxb:~/anaconda3/envs/r-tensorflow/bin$ sudo apt install graphviz
...
Run dot -Tps /tmp/tmpffo17gx5 will success now:
xb#dnxb:~/anaconda3/envs/r-tensorflow/bin$ dot -Tps /tmp/tmpffo17gx5
%!PS-Adobe-3.0
%%Creator: graphviz version 2.38.0 (20140413.2041)
%%Title: G
%%Pages: (atend)
%%BoundingBox: (atend)
%%EndComments
save
%%BeginProlog
/DotDict 200 dict def
DotDict begin
...
Restart R session, no more error:
> plot_model(model)
>
This sudo apt install graphviz is for Linux, but I hope this answer help you debug the error in Windows.
You should install the Python libraries:
pip install pydot graphviz
And also you need to download the graphviz binaries, and these are not installed with Python.
On Ubuntu you can install them with apt:
apt-get install -y graphviz libgraphviz-dev
On osX with brew:
brew install graphviz
For Windows and other operating systems, the instructions can be found at http://www.graphviz.org/