My web application allows end users to upload image. After the image is saved to server, the image will then be viewable at my web site. To make the webapp easier to scale, I decide to store the uploaded image into different folder based on current time, like:
/images/upload/2011/11/30/image1.jpg
/images/upload/2011/11/30/image2.jpg
/images/upload/2011/12/29/image1.jpg
/images/upload/2011/12/29/image2.jpg
This is ok. However the image URL for end user will also include information like:
http://www.mywebapp.com/images/upload/2011/11/30/image1.jpg
which is not desireable. I am wondering whether it is possible to produce the digest for "2011/11/30/image1.jpg" as something like "8faa6933ac54cd2ae5eb575d2d966a42.jpg", save the mapping somewhere, and then serve end user with:
http://www.mywebapp.com/images/8faa6933ac54cd2ae5eb575d2d966a42.jpg
When the request for the image comes in, we look up the real image from the previously saved mapping, and serve the real image.
Is it possible to achieve the above? Or it is not relevant at all. I am using spring mvc for my application.
Thank you for your time,
George
You could write a servlet that catches those urls and pass the image to the user as a byte-stream.
Related
I'm building a backend admin system which edits json files that control the look and feel of the main site. I want to add a 'preview' button before the user hits save. To do that, I want to use the main site, but instead of calling the actual json file in production, save a temp version of it and redirect this user's traffic for that file to the temp file - from the original site code.
i've considered both chrome pluggins, configuring iframe somehow or, in worst case scenario, grabbing the production front-end, parsing out the call to the prod json file and replacing with new temp json file. That is obviously not ideal as it would entail a lot of work and if anything changes on the prod site, this will have to be updated.
I would love your ideas!
Do you have access to the main site's source code? You could implement a preview option from the main site which accepts a GET parameter and uses a temporary JSON setting based on this GET parameter.
From the backend admin system's point of view, it's just a matter of adding the JSON as part of the ajax GET request.
Unfortunately though, there is no easy way of doing this if you don't have access to the main site's source code or if you can't reach out to whoever maintains that main site.
Your cleanest option might be to recreate the main site's look and feel instead and pass it off as a "preview".
I made this website for a client which wanted to be able to upload images and then use those images to create some dynamic content on his site. It all works fine, but now I want to isolate that administration part (where he can add images and create his content) on a subdomain.
So at the moment, I have two projects. One where images get uploaded to, and one who has to access those images (this is my problem).
I have read multiple topics related to this issue but have not found a solution, I can never get a path outside of my current project.
The only option I am thinking right now that could work is to have some kind of API on the main website, and when an image gets uploaded to the administration site, send that file over to the main site, but that seems pretty overkill knowing that my images will be on the same server.
Can this be done?
What is the cleanest/best way to achieve this?
Please note:
Saving images to the database is not an option. Uploading files on the server and then only storing the path is so much faster.
My images get uploaded at run-time, I can't use anything that relies on resources/compilation-time.
Thanks!
UPDATE (SOLUTION)
Rather than saving in the database only the name of the file (image), for example "image1.png" and then trying to retrieve the path in the other project, I ended up saving the absolute URL in the database so that I could then use that URL directly.
public static string ResolveServerUrl(string serverUrl, bool forceHttps)
{
if (serverUrl.IndexOf("://") > -1)
return serverUrl;
string newUrl = serverUrl;
Uri originalUri = System.Web.HttpContext.Current.Request.Url;
newUrl = (forceHttps ? "https" : originalUri.Scheme) +
"://" + originalUri.Authority + newUrl;
return newUrl;
}
This will give you a URL that looks like http://yourdomain/path/to/image.jpg, so you can save it directly in the database and use it as is in the other project.
The only option I am thinking right now that could work is to have some kind of API on the main website, and when an image gets uploaded to the administration site, send that file over to the main site
I think you just kind of answered your own question. That is indeed the way to go, or I should say you're on the correct direction towards a enterprise SOA architecture...you are still far from it. But, this is a good start where you start to realize that your system is growing and demanding a more robust architecture
but that seems pretty overkill knowing that my images will be on the same server.
This is a false statement because if you design it well, you can easily scale out to a different server and platform without affecting your client app(s). Let's say that in the future, the content is moved to its own server, you will only make the pertinent modifications to your "Content Service" while your client apps will not need to be changed at all, they're still pointing to the same endpoint and will never notice what's happening with the internals of the "Contents Service". What this means is that your client apps only care about getting content from the "Contents Service" without knowing where the content is actually hosted, whether in a Windows Server, a Linux server, a Sql Database, an Oracle database, in the US or China. It's not the responsibility of the client app(s) to care about how the content is handled, instead they only need to know how the content is served
Hope it makes sense. I could provide you with some links explaining the absolute benefits of such architectures
I made an ASP.NET MVC application which allows user to create dynamic websites. I need to add feature which will allow to download from server off-line version of choosen website as static html files with menu, hyperlinks, images, documents etc. It should work similar to applications such as Teleport Pro, but I have to choose from Admin Panel which content should be export.
Client wants to burn static website on CD, save on pendrive.
Do you have any ideas how to begin? Please help.
I currently have implemented that in a current project...
User is able to change anything in the frontend and at the end he can publish and download the offline files... the site subscribe users and show all prizes, winners and more information about that campaign.
All was done in ASP.NET MVC3 under .NET4 and hosted in AppHarbor.
It's composed at several applications but for what you want, you develop the Backend and the Frontend, and to generate the static files, simple use the Frontend to grab the full HTML
As an example, I can show what 2 users did...
Callme.dk did http://callme.julekal.info and
Sony Nordic did http://sony.julekal.info
plus, you can simply point custom domains to it as well like http://sonynordicxmas.net/
To publish and generate all files:
one part of the editing:
So I give the users, offline access (through the .zip file), online access (through the frontend application) and the ability of using custom domains...
I think the only way this might be possible is if you go to every single page and then use your browser to "Save" the web page script and all.
However this causes several issues;
You never quite get everything and you need to massage the HTML produced, dowload all the images etc to get the page to look right
Each html file now has an associated folder with the same name and each time you do this you will get another html file with a folder. You can combine all the folders into a single one but that leads me to item 3.
You will need to edit each html file to clear up any pathing issues if you want to share a single source folder.
Data is no longer dynamic!
You need to, if you want to link all the pages to each other, edit every single html file and resolver the anchor tags.
This is too much work and I think it actually breaks the true requirement.
Don't do it! :)
I'm using the Microsoft ReportViewer that comes with ASP.NET and have a report parameter that should be setting the value (path) of an image in my report. I'm providing the path as a complete URL right now, starting with http:// but have also tried this as an app relative path, site rooted path, etc. and for some reason the image is always showing as the red X when it exports to PDF. I'm just creating an instance of a control in code, setting the properties and exporting directly to the response stream so it acts a download.
I'm just not sure what the problem could be with the image not showing up, so if anyone has any ideas please let me know.
UPDATE 1
I've determined that I can embed the image with a URL if it is on my public web server but when I'm running in localhost the image won't embed. I have confirmed for localhost that if I paste the same URL into my browser the image will open fine. As far as I know, I don't have a proxy. So I can work around my issue, but I still don't understand what the problem is with localhost.
UPDATE 2
Forgot to mention that when the URL to the image is opened from a browser it works fine.
It is not possible for a PDF to contain a reference an external image (at least from my understanding). In order for an image to appear in the PDF, it must be embedded into the document. Therefore, to use an external image, your app must retrieve the image and store it in the document. The report viewer will try to do this for you.
Two possible answers:
First, in order for your app to package the image into the PDF, it must be able to retrieve the image from the URL you are specifying. If that URL is behind a proxy (from the perspective of your app server) and/or requires credentials to access, this will present a challenge with the default configuration of the report viewer.
If a proxy server is the issue, please see the settings to your web.config you can add below. You may also need to supply network credentials, so your app can authenticate to the proxy. There are lots of ways to solve this, but one of the easiest is to run your application as a service account on your domain that has rights to traverse your proxy. You can test this by running the site as you temporarily (should be temporary because this is a horrible security practice).
The image you are using could require credentials to access (try pulling up the image in Firefox with empty cookies and verifying whether credentials were required to access it). If it requires Windows authentication, the same solution to proxy security may apply to authentication required on the remote image. If it requires some other form of authentication, you may be better off downloading and embedding the image into your project.
It is also possible to download the image using other means in your code and convert it to a byte array for inclusion in the report. There are lots of examples of this on the web, including a Stack Overflow here.
Second, take a look at the following page:
http://msdn.microsoft.com/en-us/library/ms251715%28VS.80%29.aspx
Using external images in a
ReportViewer report is not enabled by
default. To use an external image, you
must set the EnableExternalImages
property in your code. Depending on
your network configuration, you might
also need to bypass proxy settings to
allow the external image to appear.
You can add the following settings to
the Web.config file to bypass the
local proxy. When modifying your
Web.config file, be sure to specify
the name of the proxy server that is
used in your network:
<system.net>
<defaultProxy>
<proxy usesystemdefault = "false" bypassonlocal = "true" proxyaddress = "http://< proxyservername >:80/" />
<defaultProxy>
</system.net>
Hope one or both of these helps.
Jerry
When passing external image filenames to ReportViewer parameters, pass the format like this: file://C:\app\images\pic.jpg. Anything else usually doesn't work well when deployed.
Okay, so this was our solution. The web server did not recognize its own qualified DNS name as a URL, so we had to edit the Hosts file in the C:\Windows\System32\drivers\etc folder and add the host name as localhost. The line we added to the file was:
ourserver.ourdomain.com 127.0.0.1
I don't think Adobe Reader (or maybe the PDF specification itself?) allows external content to be loaded for security purposes. I vaguely remember having a similar issue that had nothing to do with reporting services (I was dynamically generating PDFs and using variable logos and had to embed them).
Did you try a regular file path (c:/temp/somefile.bmp)? Reporting services local report reads the file from the disk and embeds it in the pdf file produced. Make sure that the identity of the app pool in IIS has read permission on the image file.
We are doing it and our images are placed in an img folder under the web site, along withe the rest of the web sites images. We avoid hard coding the path by using Server.MapPath(relative path).
Hope this helps
I fixed my problem with this:
//For local relative paths
string imgUrl = new Uri(HttpContext.Current.Server.MapPath("~/images/mylocalimage.jpg")).AbsoluteUri;
// OR
// For complete URLs
{
ServicePointManager.SecurityProtocol |= SecurityProtocolType.Tls | SecurityProtocolType.Tls11 | SecurityProtocolType.Tls12; // This allows reportViewer to download image from url
string imgUrl = /* Your image URL ("http://") */;
}
//Then pass imgUrl parameter as external source of your image.
Can the report viewer get an image from a relative url? I've never used it, so best to check that assumption.
Have you tried using the Html.Content() helper to set the URL? Whenever I have issues with my urls its because I didn't use this to generate the correct url for the view.
Let's say we have a web site with a CF app that was written in-house.
Assume that:
Server 2003 IIS6 or 2008 IIS7 will be used
ColdFusion 8 will be used
Directory browsing is denied
SSL is required to connect
The account login process is secure (yeah I know that is a whole other
ball of wax but that concept is discussed ad nauseum on the web).
Say I have a file at https://domain.com/folder1/folder2/ with a name like picture92352.ext imagine it as a jpg or pdf or whatever. The entire path between the domain name and the file varies widely in naming structure, depth, etc. Files are not all lumped together in one folder.
The app restricts links by user such that a user would have to have access to that file to find it in the first place but as it stands now if a person knew the full URL to that file they could retrieve it without logging in to the app. It's the classic security by obscurity situation. A random person isn't likely to find a file they shouldn't get to but once someone is given access they know how to access it from another PC where their actions might not be traced back to them.
How do I restrict access to these files before someone logs in and still make them accessible to outside users after they log in? Is there a way to do it with permissions only or is the only answer to have code dynamically moving files around at the time of the request or is there some obvious step I'm not even thinking of?
Let me clarify this slightly. No matter how the file is presented on a page a user can use the browser IE, Firefox, etc to examine the URL the file comes from. If the image is a link there is always copy shortcut in the right click menu for IE and the same functionality in FF is called copy link location. If the image is displayed inline as part of the page an IE user can right click and choose properties to see the URL, in FF the same functionality is present to see properties but there is an even quicker more convenient option labeled copy image location. Once a user knows the URL to a file if the location or file name doesn't change they can use that URL without authenticating in the CF app.
If I change the NTFS/share permissions so that IUSR can't see the content then my CF app and IIS can't push it. What strategy do I use to provide the file in the CF app that doesn't leave this hole open?
You could write a CFM page that serves up the images. Then you just make sure they are authenticated inside the CFM.
<!-- something like this -->
http://localhost/GetFile.cfm?file=foobar.jpg
In GetFile.cfm, you would do something like:
<!-- the filename part is what the browser will pre-popualate the file name in the download dialog as -->
<CFHEADER name="Content-disposition" value="attachment;filename=picture92352.ext">
<CFCONTENT type="text/plain" file="\\fileserver\folder1\folder2\picture92352.ext">
Take a look at the various MIME types.
If you wanted to do something similar but keep a more natural URL, I think you would need to leverage the Java servlet underpinnings of ColdFusion to create a handler for any URL matching a certain pattern.