How do I prevent IIS 7.5 from caching symlink content? - windows

I have set up IIS 7.5 to statically serve some files, and some of these files are actually symbolic links (created by mklink).
Even if I disabled both kernel and user caching, these files seems to be cached somehow by IIS. And IIS is still serving old versions after the files are modified.
To be sure that it is not caused by ASP.NET, I've created a dedicated unmanaged AppPool. I have also checked that these file are not cached by browsers.
My web.config is following:
<?xml version="1.0" encoding="UTF-8"?>
<configuration>
<system.webServer>
<directoryBrowse enabled="true" />
<caching enabled="false" enableKernelCache="false" />
<urlCompression doStaticCompression="false" doDynamicCompression="false" />
<staticContent>
<clientCache cacheControlMode="DisableCache" />
</staticContent>
</system.webServer>
</configuration>
There are several people mentioning this problem:
http://forums.iis.net/t/1166077.aspx
http://forums.iis.net/t/1171204.aspx
Any hints how to solve this problem?

This problem drove me nuts for like a month a while back. You have to disable IIS caching in the registry, as far as I know this isn't documented anywhere for IIS 7 but instead is an old IIS 5 trick that still works. You can either turn the below into a .reg file and import it or you can just navigate to the section and add it manually. I recommend rebooting after changing this parameter, I'm not sure if IIS picks it up after just an iisreset.
Windows Registry Editor Version 5.00
[HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\InetInfo\Parameters]
"DisableMemoryCache"=dword:1

I was previously able to fix this issue on IIS7 with Banin's fix. Since then, I have moved to Windows 10 with IIS 10, and suffered the same problem again. DisableMemoryCache did not help.
I then disabled kernel caching, and for now, that seems to fix the issue (I'm sorry for the Dutch in the screenshot):

Banin's solution worked for me. The issue was resolved after changing registry parameter and resetting IIS. The C# program below (you can use LINQPad to run it) will help you reproduce the issue:
using System.IO;
using System.Net;
void Main()
{
var virtualPath = "JunctionPoint/sample.js";
var physicalPath = $#"C:\IISROOT\JunctionPoint\{virtualPath}";
for (int i = 0; i < 100; i++) {
File.WriteAllText(physicalPath, i.ToString());
Console.Write(i + "=");
var client = new WebClient();
string html = client.DownloadString($"http://localhost/{virtualPath}");
Console.WriteLine(html);
if (i.ToString() != html) {
Console.WriteLine("Issue reproduced!!!");
}
}
}

Related

How do I setup Thinktecture Identity server v3 beta 1-2 with ASP.NET Identity?

I have looked at all the docs for Thinktecture Identity server v3 and have not been able to figure out how to get started using ASP.NET identity.
Can someone please explain at a high level step by step from step 1 (i.e. cloning the git repo) to it's final state which is up and running with the Identity Manager as well. Essentially I just need to know how to set this up.
The videos I see on Vimeo seem out of date (and I may be wrong because I am new to this) because now there are several repositories and in the videos I think I saw the asp.net identity user service in the same solution in core.
I am trying to prototype this for my employer (AngularJS, Identity Server, OAuth 2.0, resource owner vs implicit flow, ) and am hoping to get this working as soon as possible.
Many thanks in advance!
Andrew
Have you checked Thinktecture.IdentityManager.AspNetIdentity solution? There is example how to configure it (see Host project):
public void Configuration(IAppBuilder app)
{
var factory = new Thinktecture.IdentityManager.Host.AspNetIdentityIdentityManagerFactory("AspId");
app.UseIdentityManager(new IdentityManagerConfiguration()
{
IdentityManagerFactory = factory.Create
});
}
In order to add this functionality to the clean project you just have to add necessary packages
<package id="Thinktecture.IdentityServer.v3" version="1.0.0-beta1" targetFramework="net45" />
<package id="Thinktecture.IdentityServer.v3.AspNetIdentity" version="1.0.0-beta1" targetFramework="net45" />
and configure it in the Startup. It's not necessary to clone git repo and compile it...

How to embed a database in a visual studio solution?

I've been reading about how wonderful Visual Studio 2013's new Sql Server Data Tools are, and about the new localdb database server, etc., so I've been trying to do what would seem to me to be the point of the whole thing - to embed a local test/development database in a VS solution, so that when I check out a project into a clean directory, on a new machine, I can just run my application, connected to the database in the solution.
But I've not been able to figure out how to do it.
Can anyone give me any hints? Or directions to a tutorial?
Adding some clarification
There's a tutorial on how to include a localdb database in a project, on MSDN, here:
Local Data Overview
But, unfortunately, it doesn't work. I followed through the instructions, exactly, and it all seemed to work, until I moved the solution folder to a new location, at which point it lost track of the database.
The problem is the connection string, which contains an absolute path to where the database was when it was created. Which is useless. I need to be able to check out a project to any location, on any machine, and have it build and run there.
<connectionStrings>
<add name="ConnectLocalData.Properties.Settings.SampleDatabaseConnectionString"
connectionString="Data Source=(LocalDB)\v11.0;AttachDbFilename=E:\dev\Experiments\LocalDbWalkthrough\SampleDatabaseWalkthrough\SampleDatabase.mdf;Integrated Security=True;Connect Timeout=30"
providerName="System.Data.SqlClient"
/>
</connectionStrings>
Apparently, this question has been asked before:
Make the connectionstring's AttachDbFilename relative in config file
But that question has no answers.
So, I found the trick.
ADO allows connection strings to start with |DataDirectory| - which is a substitution string that is replaced by the "DataDirectory" setting of the current AppDomain.
This usually defaults to the location of the .EXE, though it varies with websites, click-once installs, etc.
And because EntityFramework builds on ADO, it works in EF, too.
What makes it work is that you can change it, on program start, to point anywhere you like.
What I am doing is putting an appSetting with a path relative to the location of the .EXE, in each project's App.config, and using it to set it on program start:
<appSettings>
<!-- path to the directory containing the database, relative to the location of the .exe -->
<add
key="dataDir"
value="..\..\..\DataBase"
/>
</appSettings>
<connectionStrings>
<add
name="EmbeddedDatabaseConnectionString"
connectionString="Data Source=(LocalDB)\v11.0;AttachDbFilename=|DataDirectory|EmbeddedDatabase.mdf;Integrated Security=True"
providerName="System.Data.SqlClient"
/>
</connectionStrings>
And then in code:
public class ReadWithADO
{
static ReadWithADO()
{
var appSetting = ConfigurationManager.AppSettings["dataDir"];
var baseDir = AppDomain.CurrentDomain.BaseDirectory;
var path = Path.Combine(baseDir, appSetting);
var fullPath = Path.GetFullPath(path);
AppDomain.CurrentDomain.SetData("DataDirectory", fullPath);
}
static void Main(string[] args)
{
var connectionString = ConfigurationManager.ConnectionStrings["EmbeddedDatabaseConnectionString"].ConnectionString;
using (var con = new SqlConnection(connectionString))
{
con.Open();
var cmd = new SqlCommand("SELECT * FROM Customer", con);
var rdr = cmd.ExecuteReader();
while (rdr.Read())
{
Console.WriteLine(rdr[0]);
}
}
Console.Write("<Press any key>");
Console.ReadKey();
}
}
This works just the same in Entity Framework:
<connectionStrings>
<add
name="EmbeddedDatabaseEntities"
connectionString="metadata=res://*/EmbeddedDatabase.csdl|res://*/EmbeddedDatabase.ssdl|res://*/EmbeddedDatabase.msl;provider=System.Data.SqlClient;provider connection string="data source=(LocalDB)\v11.0;attachdbfilename=|DataDirectory|EmbeddedDatabase.mdf;integrated security=True;connect timeout=30;MultipleActiveResultSets=True;App=EntityFramework""
providerName="System.Data.EntityClient"
/>
</connectionStrings>
<appSettings>
<!-- path to the directory containing the database, relative to the location of the .exe -->
<add
key="dataDir"
value="..\..\..\DataBase"
/>
</appSettings>
And:
public class ReadWithEF
{
static ReadWithEF()
{
var appSetting = ConfigurationManager.AppSettings["dataDir"];
var baseDir = AppDomain.CurrentDomain.BaseDirectory;
var path = Path.Combine(baseDir, appSetting);
var fullPath = Path.GetFullPath(path);
AppDomain.CurrentDomain.SetData("DataDirectory", fullPath);
}
private static void Main(string[] args)
{
using (var db = new EmbeddedDatabaseEntities())
{
foreach (var customer in db.Customers)
{
Console.WriteLine(customer.CustomerId);
}
}
Console.Write("<Press any key>");
Console.ReadKey();
}
}
With this you can have a local database that you use in development, or when running unit tests that aren't really unit tests. (Strictly speaking, if a test is hitting a database, it's an integration test, not a unit test, but such tests can be very useful, even if they do violate doctrinal purity.)
And since your production installations are going to use connection strings that point to real database servers, instead of to local files, none of this messing about with DataDirectory will have any effect.
Take a look into "binary resources". In addition to resources like icons, cursors, and string tables, arbitrary binary blobs can be added to the executable. One example would be to embed precompiled hlsl shaders. Another example is sysinternals processes explorer. The 64bit executable is a resource inside the 32bit executable.
If your database api expects a file to mount you may need to copy out this resource to disk. Otherwise use directly. Examples can be found in the platform sdk.

How to deploy Entity Framework with Oracle ODAC 12 on WS2012 just copying DLLs

I´ve searched the following links:
How to deploy Oracle with EF
Problems deploying Oracle with EF
And many other posts around regarding Oracle deployment.
Basically I have an C# simple test application to insert some rows into a database (this is a test application. The full application uses a lot of EF stuff):
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading;
using System.Diagnostics;
using MzDbLib.DataAccessObject;
using MzDbLib.DatabaseContext;
using MzDbLib.DatabaseModel;
namespace TestDbConnection
{
class Program
{
static void Main(string[] args)
{
Console.WriteLine("This program will generate 10 logs into SYSTEMDATALOG table");
///
/// Do a loop of 10 logs generated
///
for (int i = 0; i < 10; i++)
{
string msg = "TEST GENERATED LOG NUMBER " + i.ToString();
Console.Write("Generating log " + i.ToString() + "...");
//
// Connect to database and to the log table
//
Entities dbContext = new Entities();
SYSTEMDATALOG logTable = new SYSTEMDATALOG();
logTable.DATETIME = DateTime.Now;
logTable.TYPE = "INFO";
logTable.SEVERITY = 0;
logTable.SOURCE = "TESTDBCONNECTION";
logTable.USER = "SYSTEM";
logTable.MESSAGE = msg;
dbContext.SYSTEMDATALOG.Add(logTable);
dbContext.SaveChanges();
Console.WriteLine("Done.");
}
Console.WriteLine ("Data generated at the database. Press a key to end test.");
Console.ReadKey();
//
// Application exit
//
Environment.Exit(0);
}
}
}
The dbContext and SYSTEMDATALOG classes were generated though EF model-first from an Oracle database. I´m using Visual Studio 2012 and ODAC 12.1.0.1.0 with Oracle Developer Tools 32-bit installed on development machine. All fresh install and working pretty fine when developing.
All runs fine in DEVELOPMENT, but neve in production.
I´m using in production WINDOWS SERVER 2012. I have tried the following approaches:
a) Install WS2012 from schatch and install ODAC 32-bit version 12.1.0.1.0 fresh from Oracle site. I did run install
with ODAC 4 version.
I got "The provider is not compatible with the version of Oracle client". After some tries and some hours lost, with different approaches, I decided to go to a new method - non-installating Oracle
b) I fresh installed WS2012 and did no ORacle installation. Copied the DLLs stated in the above links and now I´m getting "Unable to find the requested .NET data provider". I´ve copied all the available Oracle DLLs from DEV machine to the WS2012 EXE directory of my application and still getting that error.
My connection string (auto-generated by VS2012) is:
<?xml version="1.0" encoding="utf-8" ?>
<configuration>
<startup>
<supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.5" />
</startup>
<connectionStrings>
<add name="Entities" connectionString="metadata=res://*/DatabaseModel.DatabaseModel.csdl|res://*/DatabaseModel.DatabaseModel.ssdl|res://*/DatabaseModel.DatabaseModel.msl;provider=Oracle.DataAccess.Client;provider connection string="data source=//ORACLESERVER1:1521/MEZAMES;password=xxx;persist security info=True;user id=MZMESDB"" providerName="System.Data.EntityClient" />
</connectionStrings>
</configuration>
This string is being generated into 2 files: TestDbConnection.exe.config and TestDbConnection.vshost.exe.config (I´m copying the bin/Debug folder to the server).
So, I need help to deploy my app to the new server. Some questions:
a) Which DLL is needed to go with the application for ODAC 12.1.0.1 ? Does that changed from ODAC 11 ?
b) Is that last error regarding EF or Oracle ?
c) Why does VS generated 2 config files ?
d) Does "providerName="System.Data.EntityClient" is the cause of the error ? If so, what DLL should be copied together.
e) Is there any tool/way to know what´s missing or with incompatible version, avoiding copying and trying methods ?
f) Is something missing on the config file ?
Thanks all for any kind of help. This is making me crazy as I´m stuck on that since the beggining of the week...
I'm not sure about the installation options for ODAC in a server environment. I know you need the Transaction module only if you're using TransactionScope in your code.
The problem you're seeing from not being able to find the provider is because Oracle changed the provider name from Oracle.DataAccess.Client to Oracle.ManagedDataAccess.Client with the 12c bits.
You need to change this in both the connection strings and in the SSDL section of the EDMX file: you will go from
<edmx:StorageModels>
<Schema Namespace="Model.Store" Alias="Self" Provider="Oracle.DataAccess.Client" (...)
to
<edmx:StorageModels>
<Schema Namespace="Model.Store" Alias="Self" Provider="Oracle.ManagedDataAccess.Client" (...)

Ajax error load Url from remote server in phonegap

I have been develop Phonegap android App. I put folder www in remote server, and in MainActivity(DroidGap) i loadUrl from server. I had config in Phonegap and App running in device ( load and show page from server). But problem when i send request by Ajax to server then it fail. It could not connect to any host. Please help me? Thanh you so much.
- MainActivity
#Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
super.loadUrl("http://172.16.3.198:8080/ServerMail/index.html");
}
- Config.xml
<access origin="*"/>
<content src="http://172.16.3.198:8080/ServerMail/index.html" />
the app does not have the internet permission. you can edit AndroidManifest.xml, and something like below:
<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
package="com.example.petro"
android:versionCode="1"
android:versionName="1.0" >
<uses-sdk
android:minSdkVersion="8"
android:targetSdkVersion="17" />
<uses-permission android:name="android.permission.INTERNET"/>
Usually you have your 'site' files local to the app, not on a remote server, otherwise there is little point to Phonegap.
Here you might find that your URL is simply not reachable. A 172.16.x.x address is local to the network the server is hosted on, perhaps your phone is not on that network, especially if you are using 3G to connect.
Also, bare in mind that depending on the phone you use, you may be using an old version of webkit. As I've developed Phonegap apps, I have run into problems with jQuery 2 and older Android releases (2.1 for example). It seems to me that what you're doing is not a good use of Phonegap, and you might be better off using a shortcut instead.

Override mime type with VS Web Dev Server

I would like to serve xbaps from the VS web dev server (cassini) to Firefox, but when served from the dev server, Firefox offers to download this file. As far as I can tell, this is because the dev server is serving the xbap file with a mime type of "application/octet-stream" instead of "application/x-ms-xbap", which works when served from IIS.
Does anyone know how to change the mime type which the dev server uses for *.xbap files?
you can't. WevDev.WebHost is fairly clumsy when issuing content-types and has a very limited range of specific content-types.
You can use CassiniDev. The latest release provides extended content-type support, including .xbap.
see http://cassinidev.codeplex.com/SourceControl/changeset/view/49870#894160 for a complete list of supported types.
Update: your problem may be that you installed FF after 3.5sp1 and do not have the NPWPF.dll in your FF plugins directory. Do you have this file?
Update 2
I have just released a version of CassiniDev that is a great drop in replacement for Visual Studio's Development server. It's enhancements include improved content-type support and integrated traffic logging/viewing.
http://skysanders.net/subtext/archive/2010/05/22/release-cassinidev-for-visual-studio-2008-a-drop-in.aspx
It probably too late now, but for others who get that problem here is how to solve it:
I solved it for mp4 videos but it is the same principal for any mime,
just revise to your needs.
I assume you use vs2012, create IHttpHandler and copy this code into it:
public class Mp4Handler : IHttpHandler
{
public void ProcessRequest(HttpContext context)
{
context.Response.ContentType = "video/mp4";
context.Response.BinaryWrite(File.ReadAllBytes(context.request.PhysicalPath));
context.Response.End();
}
public bool IsReusable{ get{ return false;}}
}
And remember to add to your web.config file under system.web:
<httpHandlers>
<add verb="*" path="*.mp4" type="[your-namespace].Mp4Handler" />
</httpHandlers>
By doing so you will not need CassiniDev to serve mp4 correctly anymore, however,
CassiniDev is not evil and worth keeping - without it I wouldn't be able to verify what the problem was in the 1st place.
Note that with VS 2010 SP1, you can now use IIS Express instead of Cassini for your web projects, which gives you full control of your MIME types.
More information: http://blogs.msdn.com/b/webdevtools/archive/2011/03/14/enabling-iis-express-support-in-vs-2010-sp1.aspx

Resources