I'm working on text game project in Python. Currently i have finished console app + sqlite database. Now I want to convert console app to web app - it will be the first web app in my life.
I want to create a simple GUI. With main logo, background image, several buttons and text zones. Example of simple GUI project:
simple gui project
I would like the logic of the application to be based on the code already created for console application. For example, by replacing the current console functions (for example print) with a function that returns data in the form of JSON. But without changing the internal logic of the function already written in Python. Is it possible?
What is the easiest way (and what technologies?) to do that?
converting a python application to a web application is not a very practical task in some cases.
I think you should use something like Flask or Django but if you don't want to complicate your life too much, there may be an alternative, and it's called PyPy.js
The first things that you must take into account in the logic of web applications, is that HTML is the skeleton of what you are going to show, so you must study it, Javascript adds dynamism to your page, such as animations and data updates without reloading the page, and the CSS to add styles to your html tags.
<head>
<script src="http://pypyjs.org/pypyjs-release/lib/Promise.min.js"></script>
<script src="http://pypyjs.org/pypyjs-release/lib/FunctionPromise.js"></script>
<script src="http://pypyjs.org/pypyjs-release/lib/pypyjs.js"></script>
</head>
<body>
<script type="text/javascript">
pypyjs.exec(
// Run Python code
'y = "hellow" '
).then(function() {
// transferring the variables we need to Javascript, in this case only 'y'.
return pypyjs.get('y');
}).then(function(result) {
// Display an alert like print in Python
alert(result);
});
</script>
</body>
that would be the same as ...
y = "hellow"
print (y)
Related
I am a newbie in programming and I have a task here I need to solve. I am trying to get the html source code of a webpage using Java / Webdriver method getPageSource(). Problem is, that page is somehow generated, probably by javascript, so the result I get is html code containing just page skeleton - a table that is empty, not filled by data. But, there is tag like <script type="text/javascript" src="/x/js/main.c0e805a3.js"></script> in the very bottom of that html code.
The question is, how can I force Webdriver to run that Javascript and give me the result - the whole source html with data. I already tried to use this (js.executeScript("window.location = '/x/js/main.c0e805a3.js'");) before calling getPageSource() but not successful.
Any help will be appreciated, thanks!
There are quite a few setups, now, that can run the Java-Script on a web-page. The most well known, I think, is likely Selenium since I think it has been around for a while. Others include karate, Puppeteer, and even an old tool called Rhino. Puppeteer is a Google, Inc. project that uses Java-Script (server-side Java-Script, called Node.js. They don't like us comparing, contrasting libraries here.
I haven't had the time to engage Selenium, yet, but I write HTML parser, search and update code all the time. If your only goal is to load a page whose contents are dynamically "filled in by AJAX calls" - and what I mean by that, you only want the contents of an HTML that would normally see when you visit the sites web-page, and you are not concerned with button presses then the one I have been using for that is called Splash This tool does have the ability to let you invoke Java-Script, but if all you want to do is see the JS on a page dynamically load the table, then, literally, all you have to do is start-the tool, and add one line to your program.
On Google Cloud Platform, these 2 lines will start a Splash Proxy Server. If you are writing your code on AWS (Amazon) or Azure (Microsoft), it would likely be similar. If you are running your code in an office on the local machine, you would have to research how to start it.
Install Docker. Make sure Docker version >= 17 is installed.
Pull the image:
$ sudo docker pull scrapinghub/splash
Start the container:
$ sudo docker run -it -p 8050:8050 --rm scrapinghub/splash
Then, in your code, all you have to do is the following:
// If your original code looked like this:
URL url = new URL("https://en.wikipedia.org/wiki/Christopher_Columbus");
HttpURLConnection con = (HttpURLConnection) url.openConnection();
con.setRequestMethod("GET");
con.setRequestProperty("User-Agent", USER_AGENT);
return new BufferedReader(new InputStreamReader(con.getInputStream()));
Change the first line of code in this example to this, and (theoretically), and dynamically loaded HTML tables that are completed with the onload page events will be automatically loaded before returning the HTML page.
// Add this line to your methods
String splashProxy = "http://localhost:8050/render.html?url=";
URL url = new URL(splashProxy + "https://en.wikipedia.org/wiki/Christopher_Columbus");
For most web-sites, any initial tables that are filled by JS/jQuery/AJAX will be filled in. If you are willing to learn teh Lua Programming Language, you can also start invoking the methods there. It has been pretty convenient for my purposes, since I am not writing web-page testing code (code that simulates user button presses). If that is what you are doing, Selenium is likely worth spending time learning / studying the A.P.I.
I'm using the Session.getEffectiveUser () command to return the results of the active user in the worksheet, but if another user enters the same sheet the results will conflict.
That is, only one can enter at a time. What can I do to keep this conflict from appearing?
Crazy solution that I thought: Is there any way that this worksheet doubles if I have 2 active users at the same time, and delete if that second user leaves?
Thx a lot!
And sorry for my bad english!
Here are the steps to deploy your code as a web app so that conflicts won't happen.
For this, you will need a front end where you will take inputs or whatever from the current user who will be accessing the web app.
Now, in your appscript screen only, you can go to File -> new -> html file, and name it as index.html or whatever you like. Code it in simple html format. Apply javascript also if you have to. For adding javascript externally, you can create another .html file and write your tag there. These all is simple html and javascript only.
Now, we have to link it with our appscript somehow. So for that, write this function in your appscipt:
function doGet(e)
{
var template = HtmlService.createTemplateFromFile('Index');
return template.evaluate()
.setTitle('YOUR_TITLE')
.setSandboxMode(HtmlService.SandboxMode.IFRAME);
}
And also write this line in your Index.html page(You can write it outside of <html> tags):
<?!= HtmlService.createHtmlOutputFromFile('JavaScript').getContent(); ?>
Now your code is ready to be deployed as web app. Go to Publish -> Deploy as web app...See that you have kept the option 'me' in Execute app as. Also, you can specify who can access your web app in the next option 'who has access to this app'.
Click update and run the latest code by clicking 'latest code' written in blue. You can also note it's URL so that you can include your web app in google sites etc.
Note that, every time you make new changes to the code, you should always choose project version 'new' and then click update.
Few tips:
To call functions of appscript from javascript, you can write like this:
google.script.run.withSuccessHandler(FUNCTION_NAME).APPSCRIPT_FUNCTION();
What it will do is, it will asynchronously call appscript function and when it is successfully executed, will execute the next javascript function named 'FUNCTION_NAME'.
How this will solve your problem?
Well, as you have deplyed the web app as 'me', whoever will run the web app will execute the code as if you yourself has executed the code, but at the same time, all featuers like Session.getActiveUser() will work individually. Hence, conflicts won't happen.
Try this yourself and you will have your doubts solved. If any queries please ask, community is always happy to help. :)
My question is really simpel, but I haven't found it yet.
I have a python script running on my server. This script reads NFC cards. (pyscard)
Everytime when there is a card the cardID must send to a webpage. I have in index.html file on my localhost.
<head>
<title>Hello!</title>
</head>
<script language="JavaScript" type="text/javascript">
function card(Cardid){
alert(Cardid);
}
</script>
<body>
</body>
</html>
There is a way to do it by selenium (driver.execute_script(command) ) Selenium is to heavy. Is there a other simple and light way to do this?
If I got you right, you need to implement AJAX. Here is simpliest example How to implement a minimal server for AJAX in Python?
If you'll need something more complex — chose one of the python web frameworks (Flask or Django) and look for tutorials how to implement AJAX with them.
If you want to push cardId to webpage you need tot use something in between like socket.IO then on a listening channel pushing the data to all websocket clients. From there you can pass it to a function like yours.
The other way to do it is a bit more limiting.
You can make Ajax call to python which reads current card holding data and use that id. But when another card is on the reader,you then have tot refresh to see the new cards data.
Opening a site economizing the data load I seem to run into a need to add more data from Python occasionally. I use Python with CherryPy and Mako for loading a site.
So, how can I make a JavaScript request from Python to pass me some more data, once the site was loaded already. I want to do that without moving away from the site. I know that JavaScript can do all sorts of things, but Python can be a real muscle for me with better debugging features.
Now, I'm not keen on Ajax. I know nothing about it and I have that fear factor that it would be quite complex.
TIA
Dennis
For example you can make with jQuery like this,
in controller you return rendered template:
def some_html():
return render('my_template.tpl')
and in the client side you can use jQuery
<script type="text/javascript">
('#result_from_server').load('/some_html');
</script>
,where result_from_server its can be id of wrapper div like
<div id="result_from_server"></div>
and /some_html, url for call your some_html() function.
Very good resurce for quick start with jQuery jqapi.com
I need to render an HTML page server-side and "extract" the raw bytes of a canvas element so I can save it to a PNG. Problem is, the canvas element is created from javascript (I'm using jquery's Flot to generate a chart, basically). So I guess I need a way to "host" the DOM+Javascript functionality from a browser without actually using the browser. I settled on mshtml (but open to any and all suggestions) as it seems that it should be able to to exactly that. This is an ASP.NET MVC project.
I've searched far and wide and haven't seen anything conclusive.
So I have this simple HTML - example kept as simple as possible to demonstrate the problem -
<!DOCTYPE html>
<html>
<head>
<title>Wow</title>
<script src="http://ajax.aspnetcdn.com/ajax/jQuery/jquery-1.7.1.min.js" type="text/javascript"></script>
</head>
<body>
<div id="hello">
</div>
<script type="text/javascript">
function simple()
{
$("#hello").append("<p>Hello</p>");
}
</script>
</body>
</html>
which produces the expected output when run from a browser.
I want to be able to load the original HTML into memory, execute the javascript function, then manipulate the final DOM tree. I cannot use any System.Windows.WebBrowser-like class, as my code needs to run in a service environment.
So here's my code:
IHTMLDocument2 domRoot = (IHTMLDocument2)new HTMLDocument();
using (WebClient wc = new WebClient())
{
using (var stream = new StreamReader(wc.OpenRead((string)url)))
{
string html = stream.ReadToEnd();
domRoot.write(html);
domRoot.close();
}
}
while (domRoot.readyState != "complete")
Thread.Sleep(SleepTime);
string beforeScript = domRoot.body.outerHTML;
IHTMLWindow2 parentWin = domRoot.parentWindow;
parentWin.execScript("simple");
while (domRoot.readyState != "complete")
Thread.Sleep(SleepTime);
string afterScript = domRoot.body.outerHTML;
System.Runtime.InteropServices.Marshal.FinalReleaseComObject(domRoot);
domRoot = null;
The problem is, "beforeScript" and "afterScript" are exactly the same. The IHTMLDocument2 instance goes through the normal "uninitialized", "loading", "complete" cycle, no errors are thrown, nothing.
Anybody have any ideas on what I'm doing wrong? Completely lost here.
You can consider using Watin. Generate your page then use Watin api to capture the generated page.
http://fwdnug.com/blogs/ddodgen/archive/2008/06/19/watin-api-capturewebpagetofile.aspx
I found Awesomium Does exactly what I need! "Windowless web-browser framework". Brilliant.
Basically you are trying to do things, which are not intended to be done in that way.
You generate HTML + Javascript to enable the browser to draw it.
You write C# to enable any kind of server side things.
Generating HTML + Javascript on server to load it into a browser on server to be able to save PNG sounds bad.
Did you think about other approaches like generating the image using server side C# component?
Basically, why do you really need to save it on server? Maybe somebody can provide better solution?
See Generating HTML Canvas image data server-side? for a PhantomJs solution (similar to Node.js, but different, single file, no install)