Selenium keeps a cache? Why my javascript isn't loaded in tests? - javascript

I have a more complicate question but I'm trying to isolate the problem to avoid confusion.
I'm testing a page using selenium. In this page there are two javascript external scripts. If you go there manually the page is working correctly but using selenium one of the javascript isn't loaded:
The script from “http://localhost:55234/static/js/common.js” was loaded even though its MIME type (“text/html”) is not a valid JavaScript MIME type.
2 add-name
Loading failed for the <script> with source “http://localhost:55234/static/js/common.js”.
Checking the source (right click => view page source) gives me correctly the template with this two lines (and the others, off course):
[...]
<!-- load global javascript -->
<script type='text/javascript' src="/static/js/common.js"></script>
<!-- load app javascript -->
<script type='text/javascript' src="/static/lists/js/lists.js"></script>
[...]
the src are clickable. Cliking the first one reload the source page without the line three and four, so without this lines:
<!-- load app javascript -->
<script type='text/javascript' src="/static/lists/js/lists.js"></script>
Clicking the second one (lists.js) gives the javascript code. But! But this code looks an (very) old version of my code. Many days old (isn't too long to be cached?). At that time all the code was in one javascript file (lists.js) and the other one (common.js) didn't existed so this can explain why isn't loaded.
Why is that? How can I update this code? If I go manually in the page I can find the real updated code.
Also can be useful to know that in my browser I recently selected 'Disable cache' in the Network tab (press F12 with firefox) and 'Disable HTTP cache (...)' in the setting just to avoid these problems. In the page opened by selenium these options are both unchecked. I tried to check both (using a breakpoint()) and reload the page but nothing changed.
I repeat, maybe the cause of this is somewhere else and there many other thing to say but I think is better to keeps things as simple as possible and open other questions when I need. Now, any of this make any sense? why my script isn't updated in days (I prefer to do not empty the cache, if possible)?
I found this code to delete the cache, should I try? It look right?
def setUp(self):
profile = webdriver.FirefoxProfile()
profile.set_preference("browser.cache.disk.enable", False)
profile.set_preference("browser.cache.memory.enable", False)
profile.set_preference("browser.cache.offline.enable", False)
profile.set_preference("network.http.use-cache", False)
self.browser = webdriver.Firefox(profile)
Here some code:
My template base.html:
[...]
<head>
[...]
<!-- load global javascript -->
<script type='text/javascript' src="{% static '/js/common.js' %}"></script>
<!-- load app javascript -->
{% block script %}{% endblock %}
[...]
my template list.html
{% block script %}
<script type='text/javascript' src="{% static 'lists/js/lists.js' %}"></script>
{% endblock %}
where common.js is in myproject/static/js/common.js, while lists.js is in myproject/lists/static/lists/js/lists.js. I call both with {% static but it should be correct.
My test.py:
class NameFormSeleniumTest(LiveServerTestCase):
def setUp(self):
self.browser = webdriver.Firefox()
self.browser.implicitly_wait(2)
def tearDown(self):
self.browser.quit()
def test_form_can_save_a_name(self):
# some code
# english = ...
self.browser.get(self.live_server_url + '/lists/add-name/')
Select(self.browser.find_element_by_id('id_namelanguage')).\
select_by_value(str(english.id))
# ...
breakpoint()
form = NameForm({'nametype': nome.id, 'gender': maschio.id,
'name': 'Remo', 'namelanguage': english.id,
'usato': 0})
print(form.errors)
form.save()
The error the test gives is (in the line form = ...):
ValueError: The Name could not be created because the data didn't validate.
and form.error is:
<ul class="errorlist"><li>nametype<ul class="errorlist"><li>This field is required.</li></ul></li></ul>
but with breakpoint() I see the javascript function to add options to the field isn't found, the field stay empty so Select() don't select nothing, and the form gives the error.
Thank you for your help

I found the problem.
From the documentation:
When running tests that use actual HTTP requests instead of the built-in testing client (i.e. when using the built-in LiveServerTestCase) the static assets need to be served along the rest of the content so the test environment reproduces the real one as faithfully as possible, but LiveServerTestCase has only very basic static file-serving functionality: It doesn’t know about the finders feature of the staticfiles application and assumes the static content has already been collected under STATIC_ROOT.
Because of this, staticfiles ships its own
django.contrib.staticfiles.testing.StaticLiveServerTestCase, a
subclass of the built-in one that has the ability to transparently
serve all the assets during execution of these tests in a way very
similar to what we get at development time with DEBUG = True, i.e.
without having to collect them using collectstatic first.
So it was loading an old version of my javascript script. Like you can read the solution is to use StaticLiveServerTestCase instead of LiveServerTestCase.

Related

Flask not Parsing the current state of my CSS: it only runs on load [duplicate]

The changes used to reflect on it when I'd refresh the page, but then it just stopped and stayed stuck on that same style. Changes I make to the html and the python code continue to reflect on it though. I read a similar question here about it, that made me notice that the terminal now says
Restarting with stat
instead of
Restarting with reloader
I tried installing the watchdog package like that thread had suggested, but that didn't work either.
You "cache bust" the CSS by appending the modification stamp of the file. Something like
css_path = os.path.join(os.dirname(__file__), 'static', 'style.css')
css_time = int(os.stat(css_path).st_mtime)
...
#app.context_processor
def inject_css_mtime()
return {'css_mtime', css_mtime}
This makes css_mtime available to templates.
<link rel=stylesheet href="{{ url_for('static', filename='style.css') }}?v={{ css_mtime }}">
When the .css file changes, its mtime will change, and browsers will know to request it again. Adjust the css_path calculation to match your app structure.
You'll need to do this for any JavaScript files, too.

Cannot get js file to execute from html with Flask in PyCharm

I'm trying to get a html page to run a js script from the static files of the host using Flask (as it's a test project it's a localhost) and for some reason every script comes back as a 404 - I'm using this file structure
¬static
¬html
¬user.html
¬js
¬script.js
https://i.stack.imgur.com/vIXzr.png
I've followed as many guides and other queries on fixing this but I don't get what else I'm missing. I've used <script src="js/script.js"></script> to call it, I've used src="{{url_for('static', filename='js/script.js') }}" in place of src="js/script.js, I've tried using just script.js instead of js/script.js, I've tried putting it in different places in the file tree and using as many ways as I can think of to call it from these places, I've downloaded plugins, I looked at official sites explaining how to create html and js and etcetera... Can't get anything to work
EDIT - solved, for some reason clearing my cache for the 2000th time fixed it. Copied the project to another device, same problem, fixed it by replacing js/script.js with static/js/script.js. That doesn't seem like that's how it should be but it works I guess
Static content in Flask loaded as follows:
<script src="{{ url_for('static', filename='js/script.js') }}"></script>
But in this case your html-template should be located in separate folder:
static
--js
scripts.js
templates
user.html
Folder templates is the default place where all html-templates are located in Flask.

Why Javascript doesn't work in my Flask app? [duplicate]

This question already has answers here:
flask does not see change in .js file
(5 answers)
Closed 3 years ago.
I have a problem with Javascript in my app. I'm using Flask and I'm working in PyCharm. My html's are in the template folder and my Javascript is in static folder, so this is external file. It's called main.js.
These are the links to javascript in the html:
<script type="text/javascript" src="/static/main.js"></script>
<script type="text/javascript" src="{{ url_for('static', filename='main.py') }}"></script>
I tried both versions and I experienced the same issue with both of them. Both links would actually work for the first load of my page on localhost but every next change in my Javascript main.js file simply just wouldn't get recognized. For instance, I put alert() in main.js just to be sure that the links work, and they worked just fine. But then I deleted alert(), put there some other Javascript code and saved it, but still, this alert() would be active even though I deleted it from the main.js file. And this new code that I put in main.js, it appeared as if it wasn't there at all. So my question is why my main.js file doesn't work?
Am I missing something here? Has anyone experienced this kind of problem in Flask or any other Python (micro)framework?
Your second reference is for a py file, not a js file:
<script type="text/javascript" src="{{ url_for('static', filename='main.py') }}"></script>
When using Flask, the above is a better alternative to full paths, so change it to:
<script type="text/javascript" src="{{ url_for('static', filename='main.js') }}"></script>
If your browser still doesn't refresh the javascript you should try to Hard Refresh the pages. On Chrome, this is done by pressing CTRLShiftR on a PC or CMDShiftR on a Mac. This should clean your cache and force reload js files.
Finally, if none of these work, you should check on your python code if the headers are being modified for a longer cache. You can 'force' a Flask request to have a shorter cache time by trying to include:
#app.after_request
def add_header(response):
response.cache_control.max_age = 300
return response
You can also try changing Flask app settings for no-cache:
app = Flask(__name__)
...
app.config['SEND_FILE_MAX_AGE_DEFAULT'] = 0
I would also try a different browser and check the network inspect tool (Chrome) to see if the files are being loaded.

Javascript running from html but not php

I've read a similar question here, but can't seem to get around it in this case, so would appreciate any clarification. I have a page in php that runs several instances of JavaScript that work on cue on localhost. However one particular instance of JavaScript (that makes an arrow hide when it scrolls beyond 10px) does not run, but when i run the same from an html version of the same php page, the arrow action works as desired. Why is this the case? Here is the code of the page in jsfiddle (exactly the same is used for respective sections in the php page.)
To clarify i have added this bit of JavaScript in the following manner at the end (after footer, before body end) of the index.php file (along with other blocks of JavaScript which work as desired for their respective targets):
<script type="text/javascript">
$(window).scroll(function () {
if ($(this).scrollTop() > 10)
document.getElementById('arr_downpoint').style.visibility = 'hidden';
else
document.getElementById('arr_downpoint').style.visibility = 'visible';
});
</script>
I have added jquery as follows (and it works for all other instances on the php page except for the arrow):
<script type="text/javascript" src="//code.jquery.com/jquery-1.11.3.min.js"></script>
<script type="text/javascript" src="//code.jquery.com/jquery-migrate-1.2.1.min.js"></script>
Lastly, there are no console errors. Would like to know why only this block of JavaScript isn't working from php, but works from HTML (while the other JavaScript instances work fine on both php and HTML), and how to find out what's wrong?
RESOLUTION: Just found that I'd erroneously added # while assigning arrowpoint id. That's why the script couldn't do anything with the arrowpoint, since <a> now had a # as part of its name. sorry about that careless oversight, for the time it may have taken to consider.
If you are trying to load the page directly from the file (your page url start with 'file://...') the problem is that the browser is trying to load jquery using the same protocol (file instead of http) because you didn't specify a protocol for the external files (the src attribute starts with '//', which mean something like "use the same protocol of the current page"). You can verify if this is the reason behind your problem, opening the browser console looking for errors like:
GET file://code.jquery.com/jquery-1.11.3.min.js net::ERR_FILE_NOT_FOUND
GET file://code.jquery.com/jquery-migrate-1.2.1.min.js net::ERR_FILE_NOT_FOUND
Uncaught ReferenceError: $ is not defined
To fix this problem, you should always run you html from a server (like Apache with PHP, as you already did) or you can write the external scripts url including the protocol (but this can cause other problems if you will run your page under https)
<script type="text/javascript" src="http://code.jquery.com/jquery-1.11.3.min.js"></script>
<script type="text/javascript" src="http://code.jquery.com/jquery-migrate-1.2.1.min.js"></script>

web application root operator and script tags

Is there any way to use ASP.NET's 'web application root' operator ~ in a script tag? If not, is there any way to mimic such behavior?
My application uses nested master pages for different sub directories; A content page uses its directory-specific master page, which uses the root master page. I'd like to be able to include my <script> tags in the root master page, so I'm not repeating code all over the place, but since I don't necessarily know the depth of the path for any given content page, I can't reliably provide paths to the scripts folder.
I considered using paths in the form /scripts/jquery.js, but since the Visual Studio development server starts the application in a subdirectory of the server root, this will not translate well to the live server. To illustrate:
<!-- dev server path -->
<script type="text/javascript" src="/my_project/scripts/jquery.js"></script>
<!-- live server path -->
<script type="text/javascript" src="/scripts/jquery.js"></script>
You can, of course see the issue. Since I am not the only developer on the project, I have very little control over what happens in the "go live" process; otherwise, it could just be a matter of removing /my_project in the "go live" process.
There are some possible cases on that.
1) For large project use the local iis5.1 or other local iis, and not the VS web that runs.
2) You can avoid the first spash and use relative paths... eg:
<script type="text/javascript" src="scripts/jquery.js"></script>
<script type="text/javascript" src="../scripts/jquery.js"></script>
so you do not force him to start from beggining.
3) You can place a literal control there and just render the script tag on Page_Load with the correct path every time
4) and you can just render the src on page
<script type="text/javascript" src="<%=ResolveUrl("~/scripts/jquery.js")%>" ></script>
I am using the 1 and 3.

Categories

Resources