URL redirect in ServiceStack loginpage - razor

In my apphost.cs file I have defined unauthorized requests to open login.cshtml.
SetConfig(new EndpointHostConfig
{
CustomHttpHandlers =
{
{HttpStatusCode.NotFound, new RazorHandler("NotFound")},
{HttpStatusCode.Unauthorized, new RazorHandler("login")},
}
});
I'm running the project self hosted. I have deployed the project to a server (Debian+Apache: ProxyPass to http://127.0.0.1:2008).
My problem is that the redirect link(querystring) links back to http://127.0.0.1:2008/People.
http://servername/login?redirect=http://127.0.0.1:2008/People
How can I override the redirect url to point to http://servername/People?

Try specifying the server url you wish to use in your config, e.g:
SetConfig(new HostConfig {
WebHostUrl = "http://servername/"
});

Related

HTTP: redirect "/foo" to "/foo/"

I have a web page currently hosted at https://somesite.zz/foo/. When loaded, that returns https://somesite.zz/foo/index.html, which loads various CSS and JavaScript using relative paths:
<link rel="stylesheet" href="default.css"/>
<script type="text/javascript" src="scripts.js"></script>
Since the paths are relative, the browser loads https://somesite.zz/foo/default.css and https://somesite.zz/foo/scripts.js and everyone is happy. The problem is when someone omits the trailing slash and loads https://somesite.zz/foo. The server still returns the contents of https://somesite.zz/foo/index.html, but now the browser doesn't realize that it is in a subdirectory so the relative paths are wrong: it tries to load https://somesite.zz/default.css and https://somesite.zz/scripts.js. Those 404, of course, so nothing works.
How can I redirect /foo to /foo/ (or otherwise make them equivalent)? I can't use JS in index.html because of my CSP: any JS needs to be in an external file, which I can't load because the paths are wrong. So this probably can't be solved using JS. This site is hosted on AWS Cloudfront + S3; is there a way to configure such a redirect there?
With a little more research, I discovered that request-triggered Cloudfront Functions can return responses, so I created the following function with the "viewer request" trigger:
function handler(event) {
var request = event.request;
var uri = request.uri;
if (uri.endsWith('/')) {
request.uri += "index.html";
} else {
var leafIdx = uri.lastIndexOf('/');
if ((-1 != leafIdx) && (!uri.substring(leafIdx+1).includes('.'))) {
return {
statusCode: 301,
statusDescription: "Redirect",
headers: {
"location": { "value": request.uri + "/index.html" }
}
}
}
}
return request;
}
The first branch of that function does the typical silent "redirect" to index.html. In the second, I check if the last path component appears to be a file or directory based on the presence or absence of a '.' in the name; anything without a '.' is interpreted as a directory and a 301 redirect is issued. Since this this is a real HTTP redirect, the browser knows to change its path, avoiding my relative-path problem.

Is there a way for me to supply the http server in NodeJS with an html file for hosting?

Current code below
const http = require('http');
const server = http.createServer(function(req, res) {
res.setHeader("Content-type", "application/json");
res.setHeader("Access-Control-Allow-Origin", "*");
res.writeHead(200);
res.end("Ping server page");
});
server.listen(8080, function() {
console.eblue("\nListening on port 8080");
console.eblue("WEB SERVER STARTED\n");
});
I just want to know if their is a way to make a fully featured site and host it using node.js
I recommend using Express (a node.js package) for web servers, which you can then serve static files - including HTML - through with express.static.
Yes (if I understood correctly), you just need to serve the html as a static file like this:
https://expressjs.com/en/starter/static-files.html

How to open local file from browser?

I'm using the following when trying to open a local file:
some document
When I click the above in a browser, it opens Finder to the folder. But does not open the file. Should I be doing something else to have the file open in Numbers?
You cannot open local files on the client. This would be a huge security risk.
You can link to files on your server (like you did) or you can ask the client for a file using <input type="file">
You can only open some types of files in browsers, like html css js and mp4, otherwise the browser will want to download it. Also remember that browsers replace spaces with %20. I recommend right clicking the file and opening it with chrome then copy that link and using it.
You can open files that are local as long as it is a file that is on the file that is trying to open another file is local.
Your issue is likely the space in the document name. Try this instead:
some document
The %20 will be read by your browser as a space.
Update
The other answer points out something I missed. The .numbers extension will not be able to be opened directly by your browser. Additionally the other answer describes the security risk this could create.
The File API in HTML 5 now allows you to work with local files directly from JS (after basic user interaction in selecting the file(s), for security).
From the Mozilla File API docs:
"The File interface provides information about files and allows JavaScript in a web page to access their content.
File objects are generally retrieved from a FileList object returned as a result of a user selecting files using the <input> element, from a drag and drop operation's DataTransfer object, or from the mozGetAsFile() API on an HTMLCanvasElement."
For more info and code examples, see the sample demo linked from the same article.
This might not be what you're trying to do, but someone out there may find it helpful:
If you want to share a link (by email for example) to a network file you can do so like this:
file:///Volumes/SomeNetworkFolder/Path/To/file.html
This however also requires that the recipient connects to the network folder in finder --- in menu bar,
Go > Connect to Server
enter server address (e.g. file.yourdomain.com - "SomeNetworkFolder" will be inside this directory) and click Connect. Now the link above should work.
Here is the alternative way to download local file by client side and server side effort:
<a onclick='fileClick(this)' href="file://C:/path/to/file/file.html"/>
js:
function fileClick(a) {
var linkTag = a.href;
var substring = "file:///";
if (linkTag.includes(substring)) {
var url = '/v/downloadLocalfile?path=' +
encodeURIComponent(linkTag);
fileOpen(url);
}
else {
window.open(linkTag, '_blank');
}
}
function fileOpen(url) {
$.ajax({
url: url,
complete: function (jqxhr, txt_status) {
console.log("Complete: [ " + txt_status + " ] " + jqxhr);
if (txt_status == 'success') {
window.open(url, '_self');
}
else {
alert("File not found[404]!");
}
// }
}
});
}
Server side[java]:
#GetMapping("/v/downloadLocalfile")
public void downloadLocalfile(#RequestParam String path, HttpServletResponse
response) throws IOException, JRException {
try {
String nPath = path.replace("file:///", "").trim();
File file = new File(nPath);
String fileName = file.getName();
response.setHeader("Content-Disposition", "attachment;filename=" +
fileName);
if (file.exists()) {
FileInputStream in = new FileInputStream(file);
response.setStatus(200);
OutputStream out = response.getOutputStream();
byte[] buffer = new byte[1024];
int numBytesRead;
while ((numBytesRead = in.read(buffer)) > 0) {
out.write(buffer, 0, numBytesRead);
}
// out.flush();
in.close();
out.close();
}
else {
response.setStatus(404);
}
} catch (Exception ex) {
logger.error(ex.getLocalizedMessage());
}
return;
}
You can expose your entire file system in your browser by using an http server.
caddy2 server
caddy file-server --listen :2022 --browse --root /
serves the root file system at http://localhost:2022/
python3 built-in server
python3 -m http.server
serves current dir on http://localhost:8000/
python2 built-in server
python3 -m SimpleHTTPServer
serves current dir on http://localhost:8000/
This s

Internet Explorer Enhanced Security Configuration(IEESC) related popup is coming after uploading project in IIS

I uploaded my project in IIS which was working fine in local but in windows server 2008 R2 it was showing the above attached issue after login(Please check the attached image). The above issue was coming because Internet Explorer Enhanced Security Configuration(IEESC) was on, so I make it off but still my page was not working.
Page Behavior: 1) No page error .Also no 404 and 403 error.(Even if CustomError mode is On)
2) Controls including grid view was not getting filled up from database by JSON call.
Solution: 1) Enable .json file extension simply follow this instructions. Open the properties for the server in IIS Manager and click MIME Types
Click "New". Enter "JSON" for the extension and "application/json" for the MIME type.
2) Add the following line in web.config file
3) If you deploy your application to IIS your URI must include your application name as well. So, as your application name is QCValueStream, then your URI must be http://localhost/QCValueStream/ManageProjects/GetManageProjectsData/5.
You can automatically detect your base Uri and have it prepend by adding a line in your master page(Asp.net web application) or shared _Layout.cshtml(Asp.net MVC):
<script type="text/javascript">
var config = {
contextPath: '#Url.Content("~")'
}
var baseUri = config.contextPath;
//or
var baseUri = '#Url.Content("~")';
//Then in your JS you prepend by:
//Incorrect JSON Call
$.getJSON('/ManageProjects/GetManageProjectsData?', { searchText: inputsearchText }, function (data) {
myData = data;
});
//Correct JSON Call
$.getJSON(baseUri +'/ManageProjects/GetManageProjectsData?', { searchText: inputsearchText }, function (data) {
myData = data;
});
</script>
Note: Check the below url to make off Explorer Enhanced Security Configuration for Administrator or user.
http://www.aurelp.com/2013/01/16/how-to-turn-off-internet-explorer-enhanced-security-configuration-step-by-step/

AngularJS and Laravel 4 routing conflict in HTML5 mode

I would like to remove the # hash from URLs using Angularjs' $locationProvider.html5Mode(true).
Example: The address bar displays http://localhost/shop instead of http://localhost/#/shop.
Everything works well untill I refresh a page. If i refresh, the following Laravel Route (defined in routes.php) is accesed
Route::resource('shop', 'ShoppingController')
not the AngularJS Route (defined in app.js)
$routeProvider.when('/shop', {
templateUrl: 'templates/shop.html',
controller: 'ShoppingController'
});
My Code:
routes.php (Laravel Routes)
Route::get('/', function() {
return View::make('index');
});
Route::resource('shop', 'ShoppingController');
app.js (AngularJS Routes)
var app = angular.module('shoppingApp',['ngRoute','SharedServices']);
app.config(function($routeProvider, $locationProvider) {
$routeProvider.when('/shop', {
templateUrl: 'templates/shop.html',
controller: 'ShoppingController'
});
$routeProvider.otherwise({ redirectTo: '/' });
$locationProvider.html5Mode(true);
});
My directory structure:
Project
/app
/...
/views
-index.php (single page application file)
-routes.php (Laravel routes)
/public
/...
/js
-angular.js
-app.js
-index.php (Laravel index file)
Tried Solutions:
Rewrite the htaccess file so that all requests are redirected to index.php (the single page application file, from where AngularJS would take over the routing). Problem: In this way the Laravel route (Route::resource('shop', 'ShoppingController'); - necessary for interaction with the database) becomes inaccessible to the AngularJS $http service:
app.js
app.controller("ShoppingController", function($scope, $http) {
$http.get('/shop', { cache: true}).
success(function(data, status) {
$scope.items = data
}).
error(function(data, status) {
console.log('Status: ' + status);
});
});
Question:
How can I solve the routing problem, so that the AngularJS route, not the Laravel Route gets accessed if I refresh localhost/shop?
From what I read, it seems like Laravel is reading the modified route when you refresh the page. In this case, you should make Laravel continue to make the original view even if it would otherwise be a 404 redirect.
Try adding the following somewhere on the Laravel side (Ex. routes.php)
App::missing(function($exception)
{
return View::make('index');
});
Note: You might want to have AngularJS's routing use .otherwise to handle pages that are not found.
A better solution is to redirect this way:
'Redirect::to('/#/' . Request::path())'
When you refresh or go to the URI directly:
'Request::path()': returns the requested URI i.e.
('/shop/categories/electronics');
AngularJS in 'html5Mode' still responds to the '#/' prefix;
If angular detects the prefix when in HTML5 mode it will remove the prefix for you.
Final solution:
App::missing(function($exception) {
return Redirect::to('/#/' . Request::path());
});
If you are using Laravel 5 then go to app/Exception/Handler.php and place the code below:
public function render($request, Exception $e)
{
if($e instanceof NotFoundHttpException)
{
return Redirect::to('/#/' . Request::path());
}
return parent::render($request, $e);
}
If you wana have more than one single page application running in html5mode or just have another use for App::missing inside a Laravel app you migh use a rewrite rule like this:
#Redirect base url of AngularJS app in html5mode
RewriteCond %{REQUEST_FILENAME} !-f
RewriteCond %{REQUEST_FILENAME} !-d
RewriteCond %{REQUEST_URI} ^/path/.+$
RewriteRule ^(path)/(.*) /path/#/$2 [R=301,L,NE]
I have another solution which I found quite useful. Rather than just making home page view, I pass in the URI to the home page, which will get checked by a controller and redirect accordingly (the Angular way). This means that if you are on myapp.com/about and you refresh, instead of taking you home, it takes you back to the page you were currently on.
routes.php: Notice that I have a URI wildcard that I pass in as an argument to the callback function, then as a variable to the view.
// Note that this must be on the bottom of your routes file because
// if you have any registered route with a similar pattern
// it will get caught by this route and never reach any registered routes you might have
Route::get('{slug}', function($slug){
return View::make('index', compact('slug'));
});
// These routes will never get hit, so move them above Route::get('{slug}')
Route::get('about', function(){...});
Route::get('contact', function(){...});
index.blade.php:
<html ng-app"myApp">
<head>
...
</head>
<body>
<!--Check if there is a variable named $slug that is set-->
<!--If it is, set hidden input with ng-model-->
#if(isset($slug))
<input type="hidden" value="{{slug}}" ng-model="slug" ng-controller="RedirectController">
#endif
<div ng-view></div>
</body>
</html>
app.js
angular.module('myApp', [])
.controller('RedirectController', ['$location', '$scope', function ($location, $scope) {
// If slug is set, redirect to that slug
if ($scope.slug) {
$location.path('/' + $scope.slug);
}
}]);
For Laravel 4.x or 5.x i use this simple and nice trick and there is no need to change .htaccess file. this trick is very simple and works for me. it doesn't redirect URL and user will stay on same URL when refresh page and page will refresh:
Route::get('dashboard/{all?}', function(){
return view('main.index');
});
here my dashboard app is my SPA. this way we can resolve 404 errors pages too.