Commit b795db71 authored by Alain Takoudjou's avatar Alain Takoudjou

Add Beremiz IDE and runtime software release

New software release for https://github.com/beremiz/beremiz.

IDE require X server with libvncserver and x11vnc to work and can be used
in a browser with deployed NoVNC.
Runtime deployed can be used to executes PLC program.
parent c6fe9c5b
# THIS IS NOT A BUILDOUT FILE, despite purposedly using a compatible syntax.
# The only allowed lines here are (regexes):
# - "^#" comments, copied verbatim
# - "^[" section beginings, copied verbatim
# - lines containing an "=" sign which must fit in the following categorie.
# - "^\s*filename\s*=\s*path\s*$" where "path" is relative to this file
# Copied verbatim.
# - "^\s*hashtype\s*=.*" where "hashtype" is one of the values supported
# by the re-generation script.
# Re-generated.
# - other lines are copied verbatim
# Substitution (${...:...}), extension ([buildout] extends = ...) and
# section inheritance (< = ...) are NOT supported (but you should really
# not need these here).
[instance]
filename = instance.cfg.in
md5sum = 07ac5fa089767ae400729ef874454e0c
[template-instance-beremiz]
filename = instance-beremiz.cfg.jinja2.in
md5sum = e7f03e0fc1ef57d87feff7d649f14be8
[template-instance-beremiz-test]
filename = instance-beremiz-test.cfg.jinja2.in
md5sum = 1613dade3a4e5210bb5cb557284c90db
[directory]
tests = ${:srv}/tests
[beremiz-x11]
rendered = ${directory:bin}/beremiz-x11
[xserver]
display-num = 42
[wmctrl]
recipe = slapos.cookbook:wrapper
command-line = {{ wmctrl_bin }}
wrapper-path = ${directory:bin}/wmctrl
environment =
XORG_LOCK_DIR=${xserver:lock-dir}
DISPLAY=${xserver:display}
[runTestSuite]
env.sh = ${beremiz-env.sh:rendered}
workdir = {{ beremiz_location }}
[beremiz-tests]
recipe = slapos.recipe.template:jinja2
mode = 0700
template =
inline:#!/bin/sh
cd {{ beremiz_location }}/tests
make test_dir=${directory:tests} xserver_command='echo "Using ${xserver:display} on Slapos X Server !";' "$@"
rendered = ${directory:bin}/beremiztest
[sikulix]
recipe = slapos.cookbook:wrapper
command-line = {{ sikulix_bin }} -v
wrapper-path = ${directory:bin}/sikulix
environment =
JAVA_TOOL_OPTIONS=-Duser.home=${buildout:directory} -Djava.io.tmpdir=${directory:tmp}
[buildout]
extends =
{{ instance_nxdtest }}
{{ instance_beremiz }}
parts +=
sikulix
wmctrl
beremiz-tests
runTestSuite
eggs-directory = {{ eggs_directory }}
develop-eggs-directory = {{ develop_eggs_directory }}
offline = true
{% set part_list = [] -%}
{% set ipv6 = (ipv6 | list)[0] -%}
{% set ipv4 = (ipv4 | list)[0] -%}
[directory]
recipe = slapos.cookbook:mkdirectory
etc = ${buildout:directory}/etc
bin = ${buildout:directory}/bin
srv = ${buildout:directory}/srv
var = ${buildout:directory}/var
tmp = ${buildout:directory}/tmp
log = ${:var}/log
vnc = ${buildout:directory}/.vnc
scripts = ${:etc}/run
services = ${:etc}/service
promise = ${:etc}/promise
ssl = ${:etc}/ssl
auth = ${:tmp}/auth
workdir = ${:srv}/workdir
framebuffer = ${:srv}/framebuffer
[gen-certificate]
recipe = plone.recipe.command
command = "{{ openssl_bin }}" req -newkey rsa -batch -new -x509 -days 3650 -nodes -keyout "${:key-file}" -out "${:cert-file}"
stop-on-error = true
cert-file = ${directory:ssl}/beremiz.crt
key-file = ${directory:ssl}/beremiz.key
[novnc-instance]
recipe = slapos.cookbook:novnc
path = ${directory:bin}/novnc
ip = {{ ipv6 }}
port = 6080
vnc-ip = {{ ipv4 }}
vnc-port = ${x11vnc:port}
novnc-location = {{ novnc_location }}
websockify-path = {{ websockify_bin }}
ssl-key-path = ${gen-certificate:key-file}
ssl-cert-path = ${gen-certificate:cert-file}
[websockify-sighandler]
recipe = slapos.cookbook:signalwrapper
wrapper-path = ${directory:bin}/websockify-sighandler
wrapped-path = ${novnc-instance:path}
[websockify-sighandler-service]
recipe = slapos.cookbook:wrapper
command-line = ${websockify-sighandler:wrapper-path}
wrapper-path = ${directory:services}/websockify
hash-existing-files = ${buildout:directory}/software_release/buildout.cfg
[novnc-promise]
<= monitor-promise-base
promise = check_socket_listening
name = novnc_promise.py
config-host = ${novnc-instance:ip}
config-port = ${novnc-instance:port}
[x11vnc]
recipe = slapos.cookbook:wrapper
port = 5901
command-line = {{ x11vnc_bin }} -forever -display ${xserver:display} -ncache 10
-noxdamage -rfbport ${:port} -no6 -noipv6 -reopen -o ${directory:log}/x11vnc.log
-usepw -rfbauth ${x11vnc-passwd:passfile} -desktop BeremizVNC
-listen {{ ipv4 }} -xkb
wrapper-path = ${directory:services}/x11vnc
hash-existing-files = ${buildout:directory}/software_release/buildout.cfg
environment =
XORG_LOCK_DIR=${directory:run}
wait-for-files =
${xserver:lock-file}
[x11vnc-listen-promise]
<= monitor-promise-base
promise = check_socket_listening
name = x11vnc_listening.py
config-host = {{ ipv4 }}
config-port = ${x11vnc:port}
[random-password]
recipe = slapos.cookbook:generate.password
storage-path = ${directory:etc}/.passwd
[x11vnc-passwd]
recipe = slapos.recipe.template:jinja2
passfile = ${directory:vnc}/passwd
template = inline:#!/bin/sh
if [ -s "${:passfile}" ]; then
echo "Password initialized.";
else
chmod 700 $(dirname ${:passfile});
{{ x11vnc_bin }} -storepasswd ${random-password:passwd} ${:passfile};
fi
rendered = ${directory:bin}/x11vnc_passwd
mode = 700
[generate-vnc-password]
recipe = plone.recipe.command
stop-on-error = true
command = ${x11vnc-passwd:rendered}
update-command = ${:command}
# Generate a fonts.conf file.
[font-config]
recipe = slapos.recipe.template:jinja2
template = {{ font_config_tmplt }}
rendered = ${directory:etc}/fonts.conf
context =
key cachedir :cache-dir
key fonts :fonts
key includes :includes
cache-dir =
${directory:etc}/.fontconfig.cache
fonts =
{{ font_dejavu }}
{{ font_liberation }}
includes =
{{ font_config_loc }}/etc/fonts/conf.d
[xserver]
recipe = slapos.cookbook:wrapper
command-line = {{ xvfb_bin }} ${:display} -screen 0 1280x1024x24
-fbdir ${directory:framebuffer}
wrapper-path = ${directory:services}/xserver
hash-existing-files = ${buildout:directory}/software_release/buildout.cfg
environment =
XORG_LOCK_DIR=${:lock-dir}
FONTCONFIG_FILE=${font-config:rendered}
display-num = 0
display = :${:display-num}
lock-dir = ${directory:run}
lock-file = ${:lock-dir}/.X${:display-num}-lock
[xserver-promise]
recipe = slapos.cookbook:wrapper
wrapper-path = ${directory:promise}/xserver-is-up
command-line = bash -c "[ -S ${xserver:lock-dir}/.X11-unix/X${xserver:display-num} ]"
[fluxbox]
recipe = slapos.cookbook:wrapper
command-line = {{ fluxbox_location }}/bin/fluxbox -display ${xserver:display}
-log ${directory:log}/fluxbox.log
wrapper-path = ${directory:services}/fluxbox
environment =
HOME=${buildout:directory}
XORG_LOCK_DIR=${xserver:lock-dir}
FONTCONFIG_FILE=${font-config:rendered}
LANG=en_US.UTF-8
LANGUAGE=en_US:en
LC_ALL=en_US.UTF-8
[beremiz-env.sh]
recipe = slapos.recipe.template:jinja2
mode = 0640
template =
inline:#!/bin/sh
export LD_LIBRARY_PATH={{ mesa_location }}/lib
export PATH=${directory:bin}:{{ autoconf_bin }}:{{ automake_bin }}:{{ matiec_location }}/bin:{{ bison_location }}/bin:{{ flex_location }}/bin:{{ bin_directory }}:{{ gcc_location }}/bin:$PATH
export XDG_DATA_DIR={{ gtk3_location }}/share
export GSETTINGS_SCHEMA_DIR={{ gtk3_location }}/share/glib-2.0/schemas
export FONTCONFIG_FILE=${font-config:rendered}
export DISPLAY=${xserver:display}
# Export pythonpath here as beremiz will use sys.executable to start internal
# processes then they won't have eggs in sys.path.
export PYTHONPATH=$(python -c "import sys; print ':'.join(sys.path)")
export XORG_LOCK_DIR=${xserver:lock-dir}
export LANG=en_US.UTF-8
export LANGUAGE=en_US:en
export LC_ALL=en_US.UTF-8
export BEREMIZPYTHONPATH={{ python_bin }}
rendered = ${directory:bin}/beremiz-env.sh
[beremiz-wrapper-base]
recipe = slapos.recipe.template:jinja2
mode = 0700
template =
inline:#!/bin/sh
. ${beremiz-env.sh:rendered}
# wait a bit for xserver
sleep 1
exec ${:command-line}
[beremiz-x11]
<= beremiz-wrapper-base
command-line =
{{ python_bin }} {{ beremiz_location }}/Beremiz.py
rendered = ${directory:scripts}/beremiz-x11
[beremiz-runtime]
<= beremiz-wrapper-base
ip = {{ ipv4 }}
port = 3000
auto-plc = 1
wx-taskbar = 0
twisted = 1
webservice-port = 8009
command-line =
{{ python_bin }} {{ beremiz_location }}/Beremiz_service.py
-p ${:port} -i ${:ip} -x ${:wx-taskbar} -a ${:auto-plc} ${directory:workdir}
rendered = ${directory:bin}/beremiz-runtime
[request-vnc-frontend]
<= slap-connection
recipe = slapos.cookbook:requestoptional
slave = true
config-https-only = True
config-type = websocket
config-url = https://[${novnc-instance:ip}]:${novnc-instance:port}
return = secure_access domain
software-url = http://git.erp5.org/gitweb/slapos.git/blob_plain/HEAD:/software/apache-frontend/software.cfg
software-type = RootSoftwareInstance
name = Beremiz VNC
[publish-connection-information]
<= monitor-publish
recipe = slapos.cookbook:publish
vnc-url = https://[${novnc-instance:ip}]:${novnc-instance:port}/vnc.html?host=[${novnc-instance:ip}]&port=${novnc-instance:port}&encrypt=1
url = ${request-vnc-frontend:connection-secure_access}/vnc.html?host=${request-vnc-frontend:connection-domain}&port=443&encrypt=1
vnc-password = ${random-password:passwd}
[buildout]
extends =
{{ template_logrotate }}
{{ ' ' ~ template_monitor }}
parts =
monitor-base
fluxbox
novnc-promise
xserver-promise
x11vnc-listen-promise
beremiz-x11
beremiz-runtime
websockify-sighandler-service
request-vnc-frontend
generate-vnc-password
publish-connection-information
eggs-directory = {{ eggs_directory }}
develop-eggs-directory = {{ develop_eggs_directory }}
offline = true
[buildout]
parts = switch-softwaretype
eggs-directory = {{ buildout_egg_directory }}
develop-eggs-directory = {{ buildout_develop_directory }}
offline = true
[switch-softwaretype]
recipe = slapos.cookbook:switch-softwaretype
default = template-{{ instance_template_type }}:rendered
RootSoftwareInstance = ${:default}
test = template-beremiz-test:rendered
[slap-configuration]
recipe = slapos.cookbook:slapconfiguration.serialised
computer = ${slap-connection:computer-id}
partition = ${slap-connection:partition-id}
url = ${slap-connection:server-url}
key = ${slap-connection:key-file}
cert = ${slap-connection:cert-file}
[jinja2-template-base]
recipe = slapos.recipe.template:jinja2
rendered = ${buildout:directory}/${:filename}
extensions = jinja2.ext.do
mode = 0644
extra-context =
context =
key develop_eggs_directory buildout:develop-eggs-directory
key buildout_directory buildout:directory
key eggs_directory buildout:eggs-directory
key ipv4 slap-configuration:ipv4
key ipv6 slap-configuration:ipv6
key global_ipv4_prefix network-information:global-ipv4-network
key slapparameter_dict slap-configuration:configuration
key computer_id slap-configuration:computer
raw bin_directory {{ bin_directory }}
raw template_monitor {{ template_monitor_cfg }}
raw template_logrotate {{ logrotate_cfg }}
raw logrotate_cfg {{ logrotate_cfg }}
raw python_bin {{ python_bin }}
${:extra-context}
[template-beremiz]
<= jinja2-template-base
template = {{ template_instance_beremiz }}
filename = instance-beremiz.cfg
extra-context =
raw autoconf_bin {{ autoconf_location }}/bin
raw automake_bin {{ automake_location }}/bin
raw bash_bin {{ bash_location }}/bin/bash
raw beremiz_location {{ beremiz_location }}
raw bison_location {{ bison_location }}
raw flex_location {{ flex_location }}
raw fluxbox_location {{ fluxbox_location }}
raw font_config_loc {{ fontconfig_location }}
raw font_config_tmplt {{ template_fonts_conf_target }}
raw font_dejavu {{ font_dejavu }}
raw font_liberation {{ font_liberation }}
raw gcc_location {{ gcc_location }}
raw gtk3_location {{ gtk3_location }}
raw matiec_location {{ matiec_location }}
raw mesa_location {{ mesa_location }}
raw novnc_location {{ novnc_location }}
raw openssl_bin {{ openssl_location }}/bin/openssl
raw websockify_bin {{ bin_directory }}/websockify
raw x11vnc_bin {{ x11vnc_location }}/bin/x11vnc
raw xvfb_bin {{ xserver_location }}/bin/Xvfb
[template-beremiz-test]
<= jinja2-template-base
template = {{ template_instance_beremiz_test }}
filename = instance-beremiz-test.cfg
extra-context =
key instance_beremiz template-beremiz:rendered
raw beremiz_location {{ beremiz_location }}
raw sikulix_bin {{ sikulix_bin }}
raw xvfb_bin {{ xserver_location }}/bin/Xvfb
raw wmctrl_bin {{ wmctrl_location }}/bin/wmctrl
raw instance_nxdtest {{ nxdtest_template }}
[buildout]
extends =
../../stack/slapos.cfg
../../component/autoconf/buildout.cfg
../../component/flex/buildout.cfg
../../component/fonts/buildout.cfg
../../component/noVNC/buildout.cfg
../../component/shellinabox/buildout.cfg
../../component/nginx/buildout.cfg
../../component/lxml-python/buildout.cfg
../../component/numpy/buildout.cfg
../../component/numpy/openblas.cfg
../../component/matplotlib/buildout.cfg
../../component/wxpython/buildout.cfg
../../component/matiec/buildout.cfg
../../component/mesa/buildout.cfg
../../component/wxwidgets/buildout.cfg
../../component/libvnc/buildout.cfg
../../component/open62541/buildout.cfg
../../component/sikuli/buildout.cfg
../../component/fluxbox/buildout.cfg
../../stack/monitor/buildout.cfg
../../stack/nxdtest.cfg
./buildout.hash.cfg
parts +=
slapos-cookbook
eggs
open62541
Modbus
instance
allow-picked-versions = true
[gcc]
# Always build GCC for Fortran (see openblas).
max_version = 0
[python]
part = python2.7
shared = false
[open62541]
# Beremiz need it to be in folder parts/open62541
shared = false
post-install =
mkdir -p @@LOCATION@@/build/bin
ln -sf @@LOCATION@@/lib/libopen62541.a @@LOCATION@@/build/bin/libopen62541.a
[eggs]
recipe = zc.recipe.egg
interpreter = python
eggs =
${wxPython:egg}
${python-cryptography:egg}
${lxml-python:egg}
${matplotlib:egg}
future
websockify
zeroconf2
enum34
pyro
twisted
nevow
autobahn
pycountry
fonttools
${beremiz-setup:egg}
opcua
msgpack
# testing
[beremiz]
recipe = slapos.recipe.build:download-unpacked
# download beremiz at revision 061ffbf0ba216b6636c18a6a372cd93f29ac62a9
url = https://github.com/beremiz/beremiz/archive/061ffbf0ba216b6636c18a6a372cd93f29ac62a9.tar.gz
#md5sum = 0f98e987e3cdf6560102071186f848a0
[beremiz-setup]
recipe = zc.recipe.egg:develop
egg = beremiz
setup = ${beremiz:location}
[download-template]
recipe = slapos.recipe.build:download
url = ${:_profile_base_location_}/${:filename}
[instance]
recipe = slapos.recipe.template:jinja2
rendered = ${buildout:directory}/instance.cfg
template = ${:_profile_base_location_}/${:filename}
python-bin = ${buildout:bin-directory}/${eggs:interpreter}
type = beremiz
context =
key autoconf_location autoconf:location
key automake_location automake:location
key bash_location bash:location
key beremiz_location beremiz-setup:setup
key bin_directory buildout:bin-directory
key buildout_egg_directory buildout:eggs-directory
key buildout_develop_directory buildout:develop-eggs-directory
key buildout_directory buildout:directory
key template_fonts_conf_target template-fonts-conf:output
key template_monitor_cfg monitor2-template:rendered
key template_instance_beremiz template-instance-beremiz:target
key template_instance_beremiz_test template-instance-beremiz-test:target
key template_logrotate template-logrotate-base:rendered
key fontconfig_location fontconfig:location
key font_dejavu dejavu-fonts:location
key font_liberation liberation-fonts:location
key logrotate_cfg template-logrotate-base:rendered
key bison_location bison:location
key flex_location flex:location
key fluxbox_location fluxbox:location
key gcc_location gcc:prefix
key gtk3_location gtk-3:location
key instance_template_type :type
key matiec_location matiec:location
key mesa_location mesa:location
key novnc_location noVNC:location
key nxdtest_template nxdtest-instance.cfg:rendered
key python_bin :python-bin
key openssl_location openssl:location
key sikulix_bin sikuli:rendered
key xserver_location xserver:location
key x11vnc_location x11vnc:location
key wmctrl_location wmctrl:location
[template-instance-beremiz]
<= download-template
output = ${buildout:directory}/instance-beremiz.cfg.jinja2
[template-instance-beremiz-test]
<= download-template
output = ${buildout:directory}/instance-beremiz-test.cfg.jinja2
[versions]
Pillow = 6.2.2
matplotlib = 2.2.5
kiwisolver = 1.1.0
cycler = 0.10.0
websockify = 0.9.0
Pyro = 3.16
zeroconf2 = 0.19.2
cython = 0.29.24
sphinx = 1.8.5
doc2dash = 2.3.0
Twisted = 20.3.0
autobahn = 19.11.2
attrs = 19.2.0
Automat = 0.3.0
zope.interface = 4.4.2
Nevow = 0.14.5
PyHamcrest = 2.0.3
constantly = 15.1.0
hyperlink = 21.0.0
incremental = 21.3.0
future = 0.18.2
pycountry = 18.12.8
fonttools = 3.44.0
idna = 2.10
PyHamcrest = 2.0.2
txaio = 18.8.1
# Required by:
# Automat==0.3.0
characteristic = 14.3.0
# Required by:
# hyperlink==21.0.0
typing = 3.10.0.0
# Required by:
# zeroconf-py2compat==0.19.10
ifcfg = 0.22
opcua = 0.98.13
# Required by:
# opcua==0.98.13
# trollius==2.2.1
futures = 3.3.0
# Required by:
# opcua==0.98.13
trollius = 2.2.1
[buildout]
extends =
software.cfg
../../component/git/buildout.cfg
[beremiz-repository]
recipe = slapos.recipe.build:gitclone
repository = https://github.com/beremiz/beremiz
branch = wxPython4
location = ${buildout:parts-directory}/beremiz
git-executable = ${git:location}/bin/git
[beremiz-setup]
setup = ${beremiz-repository:location}
depends =
${beremiz-gen-nxdtest:recipe}
[instance]
type = beremiz-test
[gen-nxdtest.sh]
recipe = slapos.recipe.template:jinja2
rendered = ${buildout:parts-directory}/gennxdtest.sh
nxdtest = ${beremiz-repository:location}/.nxdtest
mode = 740
template =
inline:#!/bin/sh
cd ${beremiz-repository:location}/tests/ide_tests/
testlist=$(ls -d *.sikuli)
rm -f ${:nxdtest}
for test in $testlist; do
if [ -z "$test" ]; then
continue;
fi
# beremiztest script is generated by the instance (call make test_dir=xxx xserver_command=xxx)
cat <<EOF >> ${:nxdtest}
TestCase(
"$test",
['beremiztest', '$test'],
cwd="""${beremiz-repository:location}/tests""",
summaryf=UnitTest.summary,
)
EOF
done
[beremiz-gen-nxdtest]
recipe = plone.recipe.command
command = ${gen-nxdtest.sh:rendered}
update-command = ${:command}
Beremiz IDE tests Software Release
##############################################################################
#
# Copyright (c) 2022 Nexedi SA and Contributors. All Rights Reserved.
#
# WARNING: This program as such is intended to be used by professional
# programmers who take the whole responsibility of assessing all potential
# consequences resulting from its eventual inadequacies and bugs
# End users who are looking for a ready-to-use solution with commercial
# guarantees and support are strongly adviced to contract a Free Software
# Service Company
#
# This program is Free Software; you can redistribute it and/or
# modify it under the terms of the GNU General Public License
# as published by the Free Software Foundation; either version 3
# of the License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
#
##############################################################################
from setuptools import setup, find_packages
version = '0.0.1.dev0'
name = 'slapos.test.beremiz'
with open("README.md") as f:
long_description = f.read()
setup(name=name,
version=version,
description="Beremiz IDE test",
long_description=long_description,
long_description_content_type='text/markdown',
maintainer="Nexedi",
maintainer_email="info@nexedi.com",
url="https://lab.nexedi.com/nexedi/slapos",
packages=find_packages(),
install_requires=[
'slapos.core',
'slapos.libnetworkcache',
'requests',
],
zip_safe=True,
test_suite='test',
)
##############################################################################
#
# Copyright (c) 2019 Nexedi SA and Contributors. All Rights Reserved.
#
# WARNING: This program as such is intended to be used by professional
# programmers who take the whole responsibility of assessing all potential
# consequences resulting from its eventual inadequacies and bugs
# End users who are looking for a ready-to-use solution with commercial
# guarantees and support are strongly adviced to contract a Free Software
# Service Company
#
# This program is Free Software; you can redistribute it and/or
# modify it under the terms of the GNU General Public License
# as published by the Free Software Foundation; either version 3
# of the License, or (at your option) any later version.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program; if not, write to the Free Software
# Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
#
##############################################################################
from __future__ import unicode_literals
import os
import requests
from slapos.testing.testcase import makeModuleSetUpAndTestCaseClass
setUpModule, SlapOSInstanceTestCase = makeModuleSetUpAndTestCaseClass(
os.path.abspath(
os.path.join(os.path.dirname(__file__), '../software.cfg')))
class TestBeremizInstance(SlapOSInstanceTestCase):
__partition_reference__ = 'B'
@classmethod
def getInstanceSoftwareType(cls):
return 'test'
def setUp(self):
self.connection_parameters = self.computer_partition.getConnectionParameterDict()
def test_url_get(self):
resp = requests.get(self.connection_parameters['vnc-url'], verify=False)
self.assertEqual(requests.codes.ok, resp.status_code)
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment