I'm trying to setting expire in private Cookie in Rust (Rocket Framework version 0.5.0-rc.1) using rocket::http::Cookie.
In rocket add_private doc I read:
Unless a value is set for the given property, the following defaults are set on cookie before being added to self:
path: "/"
SameSite: Strict
HttpOnly: true
Expires: 1 week from now
I don't understand how to set the Expires property.
I tried to create a new cookie and setting expire using .set_expires() (as in doc example), but it gives me the error: "the trait From<OffsetDateTime> is not implemented for std::option::Option<time::offset_date_time::OffsetDateTime>". The code that return the error is something like (values here only for test purpose):
use rocket::http::{Cookie, CookieJar};
use cookie::time::{Duration, OffsetDateTime};
fn handler(jar: &CookieJar<'_>) {
let mut cookie = Cookie::new("name", "value");
let mut now = OffsetDateTime::now_utc();
now += Duration::days(1);
cookie.set_expires(now);
jar.add_private(cookie);
}
I wonder if I have to use cookie crate instead of rocket::http to create the cookie, but in that case I cannot use CookieJar in the response handler because it expected a rocket::http::Cookie and not a cookie::Cookie.
Is there any other way to set an expire or a max age in private cookie using Rocket http module?
I encountered this same problem and I think I've figured it out:
Rocket uses both the cookie and time packages internally
The example code in the Rocket docs for rocket::http::Cookie actually comes from the cookie package and therefor confusingly uses use cookies::Cookie; instead of use rocket::http::Cookie.
Key thing: The docs at https://api.rocket.rs/v0.5-rc/ appear to be newer that the code that's in crates.io, and use different versions of the cookie and time crates.
So you need to use the same version or cookie or time that Rocket is using. If you're using rocket 0.5.0-rc.1 from crates.io then you need cookie 0.15 or time 0.2.11.
I was able to get my code working with these lines in my Cargo.toml:
rocket = { version = "0.5.0-rc.1", features = ["secrets", "json"] }
time = "0.2.11"
Your example code would then become:
use rocket::http::{Cookie, CookieJar};
use time::{Duration, OffsetDateTime};
fn handler(jar: &CookieJar<'_>) {
let mut cookie = Cookie::new("name", "value");
let mut now = OffsetDateTime::now_utc();
now += Duration::days(1);
cookie.set_expires(now);
jar.add_private(cookie);
}
Alternatively, I think if you use version 0.15 of cookie (you might be using 0.16.0-rc.1) then your code should work as you have it. I think it's cleaner to import Duration and OffsetTime directly from the time package though.
It looks like the latest version of Rocket in Github exposes time as rocket::time so we should be able to switch to that when final 0.5 release comes out.
Related
How do you configure Javalin to change the max request size, specifically the config to increase the max size of the query parameters on the request (avoiding 414 URI too long)?
I get 414 URI is too long when I exceed what looks like a default size of 8KB so would like to configure my Javalin server to increase that slightly.
I think it uses Jetty under the hood which has a HttpConfiguration.requestHeaderSize variable that may control it. Or there's a HttpParser._maxHeaderBytes which is checked before throwing the URI_TOO_LONG_414 exception.
I can't see how it can all be wired up...
Bearing in mind all the advice and warnings listed here... Assuming you have Javalin defined as follows in your main method:
Javalin app = Javalin.create(config -> {
config.jetty.server(MyJetty::create);
}).start();
Then you can create MyJetty to customize this and any other settings you may want to use.
A very basic example:
import org.eclipse.jetty.server.HttpConfiguration;
import org.eclipse.jetty.server.HttpConnectionFactory;
import org.eclipse.jetty.server.Server;
import org.eclipse.jetty.server.ServerConnector;
public class MyJetty {
public static Server create() {
Server server = new Server();
HttpConfiguration httpConfiguration = new HttpConfiguration();
httpConfiguration.setRequestHeaderSize(8192); // use your value here
HttpConnectionFactory httpCF = new HttpConnectionFactory(httpConfiguration);
ServerConnector httpConnector = new ServerConnector(server, httpCF);
httpConnector.setPort(8080); // use your port here
server.addConnector(httpConnector);
return server;
}
}
This only sets up a simple insecure HTTP connection - but shows one way to change the HttpConfiguration value for Javalin. You can use the same approach for other connectors you may want to configure, including ones using SSL/TLS.
I am assuming the latest version of Javalin (version 5) since there were some syntax changes from Javalin 4 to 5 - and also the version of Jetty changed from 9 to 11.
If you are using Javalin 4, the config syntax is a bit different:
config.server(MyJetty::create);
But I don't think the Jetty code changes (for this specific setting, at least).
Only change the HttpConfiguration, it will inform the HttpParser.
You should be leery of doing this because ...
many browsers do not support that large of a query.
3rd party internet security software on laptops will reject that exchange.
you open yourself to various old school DoS (Denial of Service) attacks related to hashmap/hashcode abuse. (to minimize this issue, use Java 17 or newer)
If you move to HTTP/2 (or HTTP/3) many servers will reject the extension of the maximum request headers (at the HTTP level) that would be needed to support this massive request path.
Also, depending on what technology Javalin is using, you might need to also increase the ContextHandler maxFormContentSize and/or maxFormKeys.
If you have reached this need, it screams of abuse of the HTTP spec, you should investigate moving to a traditional HTTP POST with Content-Type: application/x-www-form-urlencoded instead.
I'm running headless chrome in a lambda layer (https://github.com/alixaxel/chrome-aws-lambda).
Issue is, I am trying to call .toLocaleString("en-AU"), but everything comes out as UTC/GMT regardless. I have read that node didn't always ship with internationalization options. I'm assuming something along those lines is what is going on here.
Any suggestions for how to work around this?
You can use moment.js for better control over time and time formats in NodeJS Lambda
https://momentjs.com/timezone/
var newYork = moment.tz("2014-06-01 12:00", "America/New_York");
var losAngeles = newYork.clone().tz("America/Los_Angeles");
var london = newYork.clone().tz("Europe/London");
newYork.format(); // 2014-06-01T12:00:00-04:00
losAngeles.format(); // 2014-06-01T09:00:00-07:00
london.format(); // 2014-06-01T17:00:00+01:00
Check their announcement about it's future and complications, including internationalization
https://momentjs.com/docs/
So in my Test Plan I have a Cookie Manager setup inside my Thread Group which sets a specific Cookie value for 1 Cookie. Let's call it, MYID. I'm trying to figure out a way to verify that this specific Cookie's value was used to complete this one HTTP Request, because if I set my MYID to a specific value *(which actually tells which web server to go to), say to "Server1", but Server1 is down, unavailable, etc... HAProxy should change this and send you to Server2.
So basically I want to try and make sure that Cookie MYID was equal to "Server1" all the way through the HTTP Request.
I am trying to use a BeanShell PostProcessor to verify the Cookie's value after the request is ran, but when I tried using some code I have inside a PreProcessor that sets a cookie in a different Test Plan of mine I get an error saying:
Error Message:
Typed variable declaration : Attempt to resolve method: getCookieManager() on undefined variable or class name: sampler
And below here is the Code slightly modified from a BeanShell PreProcessor in another Test Plan I have...
CODE:
import org.apache.jmeter.protocol.http.control.Cookie;
import org.apache.jmeter.protocol.http.control.CookieManager;
CookieManager manager = sampler.getCookieManager();
for (int i = 0; i < manager.getCookieCount(); i++) {
Cookie cookie = manager.get(i);
if (cookie.getName().equals("MYID")) {
if (cookie.getValue().equals("Server1")) {
log.info("OK: The Cookie contained the Correct Server Number...");
} else {
log.info("ERROR: The Cookie did NOT contain the Correct Server Number...");
}
break;
}
}
For the error, I was thinking the "sampler" object was no longer available since the Request was already run, or something along those lines, but I'm not sure...
Or, is there another JMeter object I should be using instead of the "BeanShell PostProcessor" in order to verify the Cookie's value was correct..?
Any thoughts or suggestion would be greatly appreciated!
Thanks in Advance,
Matt
If you trying to get cookie manager from the parent sampler in the Beanshell PostProcessor - you need to use ctx.getCurrentSampler(), not "sampler" as it is not exposed in script variables.
So just change this line:
CookieManager manager = sampler.getCookieManager();
to
CookieManager manager = ctx.getCurrentSampler().getCookieManager();
And your script should start working as you expect.
ctx is a shorthand to JMeterContext instance and getCurrentSampler() method name is self-explanatory.
For more information on Beanshell scripting check out How to use BeanShell: JMeter's favorite built-in component guide.
We are trying to create a cookie in the PeopleSoft Peoplecode by using the %Response object.
However, the code we tried is failing.
&YourCookie = %Response.AddCookie("YourCookieName", "LR");
Another snippet we tried to create the cookie
Local object &Response = %Response;
Local object &YourCookie;
&YourCookie = &Response.CreateCookie("YourCookieName");
&YourCookie.Domain = %Request.AuthTokenDomain;
&YourCookie.MaxAge = -1; /* Makes this a session cookie (default) */
&YourCookie.Path = "/";
&YourCookie.Secure = True; /* Set to true if using https (will still work with http) */
&YourCookie.Value = "Set the cookie value here. Encrypt sensitive information.";
The document reference points to IScript functions called CreateCookie methods etc.
http://docs.oracle.com/cd/E15645_01/pt850pbr0/eng/psbooks/tpcr/chapter.htm?File=tpcr/htm/tpcr21.htm
However, these don't work in Peoplecode. We don't have the knowledge to create IScript or use it. Any insight with the People code API for cookies or IScript is much appreciated.
I just tested on PeopleTools 8.54.11 and was able to create a cookie using the snippet you provided above.
I did find I had an issue if I set
&YourCookie.Secure = True;
in an environment where I was using HTTP.
If you set Secure to False the cookie will be available in both HTTP and HTTPS
if you set Secure to True the cookie is only available in HTTPS
PeopleTools 8.54 Documentation showing the CreateCookie method
I have been trying to do this (same code snippet) from within signon peoplecode, tools release is 8.54.09. I can execute the first two lines of code, but as soon as the line of code executing the CreateCookie() method executes, I get tossed out / end up on the signon error page.
This seems to support the previous answer saying that the API has removed the method, but the answer before that says it has been successful on tools 8.54.11 -- does that mean they removed it, then put it back, and I happen to be stuck with a release where it was removed? :-/
I am using Node.js 0.2.3 and response.headers['set-cookie'] seems to be truncated after the first cookie. Is there any way I can just read the raw headers?
BTW, the set-cookie header should contain:
id1=sw34rwdsfsd;secure;
id2=wer235sd2354;secure;
id3=df435df4543;secure
My guess would be it is not parsing the boolean attributes right and stops after the first one. Anyone know if this is fixed in later versions of Node.js (even though I can't upgrade just yet)?
var spawn = require('child_process').spawn;
function getHeader(url, callback){
var client = spawn('curl', ['-I', url]);
client.stdout.setEncoding('***');
client.stdout.on('data', function(data){
callback(data);
});
}
The -I flag asks curl for just the header. Pass whatever encoding to setEncoding - I think it defaults to the raw that you're looking for.