Closed. This question needs to be more focused. It is not currently accepting answers.
Want to improve this question? Update the question so it focuses on one problem only by editing this post.
Closed 3 years ago.
Improve this question
I have created a JIRA gadget. When I put only one instance of it on a dashboard, it's fine. When I put a second instance on the same dashboard, configure it to load different data, and then refresh the whole dashboard, I can see that they share most data -- as if they get their data from the server at almost the same time and then write to the same javascript variable and then render based on that variable.
When they render, they're mostly identical to each other when I know they should be totally different (I can see values that match instance A's configuration appearing in instance B).
Another way I can tell it's wrong is when I refresh each gadget separately, they display the correct data. But when I refresh the entire dashboard, they display mostly the same thing.
How do I keep these separate? One thought I had was to try the following:
Keep a thread-safe request counter on the server.
For each request, increment the counter and append the new value to the names of javascript variables in the velocity template.
When adding items to the context hash map, append the request counter to the keys so they match the javascript variables in step 2
The renderer takes the modified velocity template and the context hash map and produces something that refers to only its own request results.
But I'm having some trouble with step 2. I have the 'location' of the template file "/templates/gadgets/my-gadget.vm" -- it's not a real location in that there is no such file on the server at that path. The renderer expects the 'location' as an argument. I want to load /templates/gadgets/my-gadget.vm (wherever it actually is), write out a new /templates/gadgets/my-gadget..vm, and then pass this new location to the renderer... But /templates/gadgets/my-gadget.vm is not an ordinary file path. Where is it?
Or is there a better approach?
Note: nothing in the servlet is marked static or volatile -- everything in the servlet is instance-specific (and therefore request-specific ???) so the bleeding between requests is on the client side (see comments for discussion on whether this is correct and see the accepted answer for the tl;dr).
You mentioned in the comments that you were storing values passed in from the HttpServletRequest as "instance variables" on the server side. The issue is that JIRA only ever instantiates a single copy of your servlet object, meaning that anything you write to an instance variable will be shared between requests. If both requests come in at the same time and they get interleaved, thread #1 will see data from thread #2 by accident, which is probably what happened.
The solution is to keep everything on the stack. For example, instead of writing to instance variables, just declare local variables inside your service method and leave everything there instead of at the class scope.
If you already have other functions in your servlet class that are using the instance variables, you can either modify them to receive the values passed over as parameters during the method call, or else refactor and move that code to another class that uses its own instance variables (but make sure you explicitly instantiate a new object of that class within service() every time you receive a request!).
Related
I am currently developing a GraphQL API with NodeJS and I am looking for a smart way to share code between create and update entity functions.
Context
In my application, users are able to create and update their own flights (as a pilot) so I have two GraphQL input fields (CreateFlightInput and UpdateFlightInput) that are called from two different mutations.
Problem
When a user creates a flight, he must provide the plane he flew with. As the plane is represented by a Mongo ID, the API needs to check if the plane exists and if the user can see it. But when the user updates a flight, the same check is required (because the user can change the plane he used). As I am using two resolvers (mutations), I don't want to write the same code twice especially since I have the same problem for the passengers' field. You will ask me that if all the checks are the same, why am I using two different resolvers? The problem is that the server must perform certain actions during create but not during update. To summarize, we have two resolvers sharing some similar code but not only.
Do you have an idea of where I could write that code that I can reuse for both? I was thinking of a function with a boolean that indicates if we are editing or not but I would know if there is (are) better method(s).
Thanks for your help.
Say you have an object formatted something like the following in one script (javascript)-
var person = {
firstName:"John",
lastName:"Doe",
age:50,
eyeColor:"blue"
};
Is there an intuitive way to "send" this object to another (javascript) script? Basically, i'm trying to communicate data within 2 scripts on a webpage and attempting to avoid having one big script, which would eliminate this problem.
I've already messed around with simply creating a div with a bunch of inner div's which hold the information from the object (All it's holding is text/numbers) but I feel like there has to be a better way of doing this in either javascript or jQuery.
Javascript files are not nodes on a network or system components. They do not "send" or "receive" anything. They are just bits of text that don't do anything by themselves at all.
Rather, your browser loads Javascript files, interprets them, and executes them. They are all loaded into a single, common sandbox and they all share the global namespace. The idea that data is sent from one script to another is simply a misunderstanding of how this all works. If you ask developers how to send data between scripts, they are going to have trouble answering, because the question is more or less gibberish. You have to post your code and be specific about the problem you are having.
If you are receiving an error like "ReferenceError: X is not defined" it is probably because X does not exist in the scope of the function that is throwing the error. For example, if you declared X with the var keyword within a function block and then attempted to access X from another function. If you wish to access a local variable from another function, you will have to pass it as a function argument or parameter.
I can provide a much more precise answer if you post your code.
Let's say I'm on a screen editing a post (and its associated meta-data). Now, the post has many categories, tags, and possibly other related items (hasMany).
When saving the entire post, I have to save the post and every single entity associated with it. This is how I do it in AngularJS:
All the data is stored in a separate model so that it can be universally accessed. Each related entity has multiple meta-data indicating whether they're new, dirty, or whether they have server-side validation errors.
A different controller called "SaveCtrl" manages saving. It goes through all the entities of a post, figures out the ones that have changed, and only sends them along with the post to a single save endpoint.
I have a factory that parses the response from the server. An element might not get saved due to a server-side validation error. Regardless, once we get the response, each of those entities have to be updated with the new state and validation errors. This allows the server-side to update entities without any errors, while returning errors for the few that did have validation errors.
Now, here are some problems with this approach:
The saving is not entirely RESTful. While retrieving data, I believe I should probably make multiple GET calls for each resource (URL design for an API). However, I don't know of a similar approach for saving. Should I save a collection, or a single entity at a time?
The meta-data for each entity (specifying whether it's new, dirty, saved, or unsaved) has to be put in the model data itself. Since ng-repeat creates a separate scope, I'd ideally like to save such state information in these separate scopes, with the ng-repeat elements wrapped in a controller that'd handle this.
My question
Which strategy should I use to save an entire post with all its related entities? Or is my present strategy good enough? Let me know if there are some additional details required.
Closed. This question needs to be more focused. It is not currently accepting answers.
Want to improve this question? Update the question so it focuses on one problem only by editing this post.
Closed 9 years ago.
Improve this question
According to this article
http://www.mediaevent.de/javascript/globale-lokale-variablen.html
Global variables are in JS pretty dangerous.
I'm sorry that it's in German, but I'm gonna point out out the 2 main statements of the article.
The first is already in the 2nd paragraph of the head statement.
It says something like "In JS global var's are dangerous as they can get accessed by other scripts over the name" That's fine so far, as that's mostly the way why I want to use global var's don't I?
But in the article it sounds as this could happen randomly. and that's for sure not the expected behaving, is it?
But what is much more frightening me is the second last sentence. It forecasts that memory leaks will generated if a function that declares a
global variable is called multiple times.
But how could this happen if the name is still the same? how there can be multiple vars declared global with the same name?
Or is this article probably written by some one just "half-knowledge"? Or maybe just addressed to some one who isn't used to the difference between global and local at all?
Or is JS really behaving in this way?
Now a concrete example:
I want some one who logs in to my page to create a Random generated token and submit it by clicking login.
on each other button I want that this token is accessed by a different function and just submit it, so that just for a new login the key will be regenerated.
For that key I was thinking about using a global variable, which gets declared by one function and gets returned by another.
But as I will generate/regenerate the key possibly more then once, would this generate memory leaks? Or is this article I'm referring to probably just dramatizing?
If this is really the way JS is behaving, what would be a good way to make a variable accessable from different functions in my case?
The problem with globals is not memory, and it's not performance.
The problems with globals is entirely different. The problems are that they introduce global state and that scripts are not bound to a namespace.
Let's go through these problems one by one.
Having global state
This is the biggest issue here. Coding necessitates that the dependencies of a module be explicit and that communication between pieces of code is very clear.
When you have global variables which part of the code uses the variable is not nearly as clear and you can't be sure what part of the code needs it and what does not.
Let's say I have a Zoo project and I have a Bathe service that cleans an animal. Instead of passing Bathe around to each animal that needs it I have it on a global namespace and I just call Bathe(myAnimal).
Now I want to restructure my zoo and I want to know which animals need bathing because I want to optimize that. I have no way of knowing that other than going through my whole code. In order to see if my Giraffe needs bathing I have to read the entire code of the Giraffe class. If instead I passed Bathe to the constructor of Giraffe instead of using it or creating it inside giraffe (a concept called dependency injection) I can see that a Giraffe needs bathing just by reading the signature.
Now this can get way worse, what if I have state? If I'm actually changing a global variable in multiple places it becomes extremely hard to track. In a more than a few lines code base this means that you have state changing all around and no clear indication of who is changing it.
This is the main reason you should avoid globals altogether .
Scripts are not bound to a namespace
If I have two scripts on a page and my first script declares a A variable on the global namespace, the second script can access that variable. This is useful because scripts can interact this way but it's very harmful because it means that scripts can override each other's code, and communicate in an unclear way.
This of course is completely mitigated if you use a module loader like browserify or RequireJS which means your whole script only exposes two globals - require and define and then script loading is done through the loader.
This way the way independent pieces of code interact is well defined. That doesn't prevent you from creating variables on the global object, but it helps mitigating the need to do so in a uniform manner.
A note on security
Of course, anything on the client side is compromised, you can't do security or anything like that in client side JavaScript on an insecure browser (that is, you didn't prevent anything external on) because the client can just run arbitrary code on your code and read it.
There are three big problems with global variables:
name collisions
code complexity
garbage collection
Name collision
The problem with having variables in global scope is that you have less control over what else is in that scope. Your code uses a ga_ variable globally and works fine, but when you add a Google Analytics snippet that uses the same variable things unexpectedly fail and it can be quite hard to see why your shopping cart fails 2 out of 3 page loads.
If you can wrap your code in an IIFE to prevent having any variables in global scope, you should do that. Obviously there are cases where you actually want to have your code accessible globally (ex: jQuery library). In those cases, it is best practice to keep all your stuff in a single namespace (jQuery) with a relevant name.
Code complexity
It is usually a good idea to partition your code so that individual pieces have minimal interactions with each other. The more pieces interact the harder it is to make changes and to track down where bugs come from. Obviously a global variable can be accessed anywhere so when you have a problem with some code that accesses a global variable, you have to inspect every usage of that variable which can be quite a big pain. The thing to do to avoid these pains is to keep variables as local as they can be and encapsulate pieces of code so they can't interact with each other except through specific interfaces.
Memory leaks
In JavaScript you have little control over the garbage collection process. All that is guaranteed is that if you can access a variable it will not be garbage collected. This means that if you want something to be garbage collected, then you must make sure you can't access it anymore. While a global i variable which keeps a number won't be a big deal, as #Boluc Papuaccoglu mentioned when your global variable keeps more and more properties over time (an array of XHR requests for example, or array of created DOM objects), the memory consumption turn into a big deal.
All of these situations are worst case scenarios and you probably won't have issues with a small application. These recomendations have most value when you're starting to learn programming because they develop good habits and when you're working on complex applications when they save you time and money wasted on debug or difficult to do improvements.
Regarding memory leaks: Let's say you have a function, and within it you define a var, and use it for some purpose then return from the function. In this case, the memory used by the variable will be freed. However, if you relied on a global variable to do the same thing, then the memory would continue to be allocated long after your function exited. Extending the same scenario, imagine that your function adds properties to this variable with names that depend on the data the function is processing (like Order ID, Customer Name, etc.) Now, each time your function gets called, more and more properties will be appended to this variable and it will grow and grow.
This question is by necessity a bit general; it relates to the overall architecture of client side applications built with javascript and jquery:
I'm building a jquery based quiz application. For initial purposes I am trying to develop it entirely client side, with all the question and answer data stored in object literals in the js files (I'm not particular concerned right now that the data would be exposed in the source). I want to build it so that this implementation could readily be adapted into an ajax solution where the question data would be pulled from a php file or database.
I've written a question generation function which takes in the object literal describing the question and renders it as html and inserts it onto the page. My question is what would be the best practice for storing the users answer data and implementing the i/o as the user proceeds through the quiz. The questions would be displayed sequentially and there will be a logic which selects from a two dimensional grid of questions to determine which question would be rendered next based on whether the user answered correctly and the coordinate position on the question grid of the question they were on.
Happy to post any code I've already written if this would be helpful to providing an answer. Thanks.
The same principles apply.
Your entry point for the program will be some function which is attached to some event which kicks everything off. Typically this will be the page load function.
In this function you will set up the program (as you would in a C++ main), create variables (global or otherwise) representing program state etc. I'd guess you'd have some logic which selects and presents a question plus perhaps a 'Ok' button which the user should click once he's happy with his user. At this point the browser is just waiting for user input, the user selects his answer and clicks ok. The logic of your program is probably store the answer in a variable somewhere and calculate the next question to display. For this you have added a function to the onclick event handler which implements this logic. You present the next question and voila you are back at the start of your loop.
I'd recommend getting the simple loop aspect working to get comfortable with javascript and the event model rather than worrying about whether global variables are bad or not. Your going to have at least one global variable in any case probably a reference to a more complex ApplicationState object.
I'm not sure if its part of your confusion but you know that instead of :
button.onclick = new function() { // loads of program code to get next question };
you can do
function NextQuestion() {
// code to get next question
}
button.onclick = NextQuestion;