AWS .NET SDK on Linux - aws-sdk

I am currently moving an ASP.NET application made by a third party from Windows to Linux. I read the documentation and nothing indicates this should be a problem, but sadly
var profile = new CredentialProfile(profileName, credentials) {
Region = RegionEndpoint.EUWest1
};
var netSDKFile = new NetSDKCredentialsFile();
netSDKFile.RegisterProfile(profile);
throws the following exception
Unhandled Exception: Amazon.Runtime.AmazonClientException: The encrypted store is not available. This may be due to use of a non-Windows operating system or Windows Nano Server, or the current user account may not have its profile loaded.
at Amazon.Util.Internal.SettingsManager.EnsureAvailable()
at Amazon.Runtime.CredentialManagement.NetSDKCredentialsFile..ctor()
Is the Amazon .NET SDK(or a part of it) not supported on Linux? If that is the case, is there a possible workaround?

For the most part there is very little that isn't supported on Linux that is supported on Windows. Off of the top of my head I can't think of anything besides NetSDKCredentialsFile which is due to the fact it uses Win32 API to encrypt credentials.
You can use SharedCredentialsFile to register a profile in the credentials file stored under ~/.aws/credentials. This is the same credential stored supported by all of the other AWS SDK and Tools.

Following on from Norm's answer, I found this resource that explained how to use Shared Credentials: https://medium.com/#somchat/programming-using-aws-net-sdk-9ce3f5119633
This is how I was previously using NetSDKCredentials, which won't work for Linux/Mac OS:
//Try this code on a non-Windows platform and you will see the above error
var options = new CredentialProfileOptions
{
AccessKey = "access_key",
SecretKey = "secret_key"
};
var profile = new CredentialProfile("default", options);
profile.Region = RegionEndpoint.USWest1;
NetSDKCredentialsFile file = new NetSDKCredentialsFile();
file.RegisterProfile(profile);
But I was then able to use this example to use SharedCredentials:
var credProfileStoreChain = new CredentialProfileStoreChain();
if (credProfileStoreChain.TryGetAWSCredentials("default", out AWSCredentials awsCredentials))
{
Console.WriteLine("Access Key: " + awsCredentials.GetCredentials().AccessKey);
Console.WriteLine("Secret Key: " + awsCredentials.GetCredentials().SecretKey);
}
Console.WriteLine("Hello World!");
You'll then be able to see your code is able to access the keys:
Access Key: A..................Q
Secret Key: 8.......................................p
Hello World!
I then used System.Runtime.InteropServices.RuntimeInformation.IsOSPlatform() (as I am using this code on both Windows and Linux), to determine which credentials to use:
using System.Runtime.InteropServices;
//NETSDK Credentials only work on Windows - must use SharedCredentials on Linux
bool isLinux = System.Runtime.InteropServices.RuntimeInformation.IsOSPlatform(OSPlatform.Linux);
if (isLinux) {
//Use SharedCredentials
} else {
//Use NetSDKCredentials
}
You may find this section of the AWS documentation helpful, too: https://docs.aws.amazon.com/sdk-for-net/v3/developer-guide/net-dg-config-creds.html#creds-locate

Related

Trying to get Google Drive to work with PCL Xamarin Forms application

I’m using Xamarin Forms to do some cross platform applications and I’d like to offer DropBox and GoogleDrive as places where users can do backups, cross platform data sharing and the like. I was able to get DropBox working without doing platform specific shenanagins just fine, but Google Drive is really giving me fits. I have my app setup properly with Google and have tested it with a regular CLI .NET application using their examples that read the JSON file off the drive and create a temporary credentials file – all fine and well but getting that to fly without access to the file system is proving elusive and I can’t find any examples on how to go about it.
I’m currently just using Auth0 as a gateway to allow users to provide creds/access to my app for their account which works dandy, the proper scope items are requested (I’m just using read only file access for testing) – I get an bearer token and refresh token from them – however when trying to actually use that data and just do a simple file listing, I get a 400 bad request error.
I’m sure this must be possible but I can’t find any examples anywhere that deviate from the slightest of using the JSON file downloaded from Google and creating a credentials file – surely you can create an instance of the DriveService object armed with only the bearer token...
Anyway – here’s a chunk of test code I’m trying to get the driveService object configured – if anyone has done this or has suggestions as to what to try here I’d very much appreciate your thoughts.
public bool AuthenticationTest(string pBearerToken)
{
try
{
var oInit = new BaseClientService.Initializer
{
ApplicationName = "MyApp",
ApiKey = pBearerToken,
};
_googleDrive = new DriveService(oInit);
FilesResource.ListRequest listRequest = _googleDrive.Files.List();
listRequest.PageSize = 10;
listRequest.Fields = "nextPageToken, files(id, name)";
//All is well till this call to list the files…
IList<Google.Apis.Drive.v3.Data.File> files = listRequest.Execute().Files;
foreach (var file in files)
{
Debug. WriteLine(file.Name);
}
}
catch (Exception ex)
{
RaiseError(ex);
}
}

How to access app's certificate store in Windows Phone 8.1 Runtime App

I'd like to access my app's certificate store from another app. I have already enabled "sharedusercertificates" in the package.appmanifest file.
Windows.Storage.StorageFile selectedCertFile = await folder.GetFileAsync(fileName);
IBuffer buffer = await FileIO.ReadBufferAsync(selectedCertFile);
string certificateData = CryptographicBuffer.EncodeToBase64String(buffer);
string password = "password";
await CertificateEnrollmentManager.ImportPfxDataAsync(
certificateData,
password,
ExportOption.NotExportable,
KeyProtectionLevel.ConsentWithPassword,
InstallOptions.None,
selectedCertFile.DisplayName);
In my own app, I can list the installed certificates without a problem:
protected override void OnNavigatedTo(NavigationEventArgs e)
{
var task = CertificateStores.FindAllAsync();
task.AsTask().Wait();
var certlist = task.GetResults();
Debug.WriteLine("Cert count: {0}", certlist.Count);
LoadCertList(certlist);
}
private void LoadCertList(IReadOnlyList<Certificate> certificateList)
{
listbox1.Items.Clear();
foreach (Certificate cert in certificateList)
{
listbox1.Items.Add(cert.Subject);
}
}
If I try to access those from another app, It will not be listed.
In the Windows Phones 8.1's mail client settings, the installed certificate is missing, too. Certificates which have been installed regularly, not programmaticaly, are listed.
Is there a way to install my custom certificates to the system's certificate store? So it can be used in other apps.
I have been searching the web for days now, but I didn't find a solution.
Due to this, it should be possible.
"The sharedUserCertificates capability grants an app container read access to the certificates and keys contained in all user stores and the Smart Card Trusted Roots store. "
https://msdn.microsoft.com/en-us/library/windows/apps/hh465025.aspx
Did I miss something? Help will be much appreciated.
Dino
If you want a certificate to be accessible for other Apps, you need to enroll it using CertificateEnrollmentManager.UserCertificateEnrollmentManager.ImportPfxDataAsync rather then CertificateEnrollmentManager.ImportPfxDataAsync.
Please note that there is no way of deleting the shared certificate unless it's expired (using InstallOptions.DeleteExpired as a Parameter in ImportPfxDataAsync).
Also, the more certificates you share this way, the slower the queries against the certificate stores get.

MQTTSource Operator compilation error in IBM Infosphere Streams

System : Running VMPlayer on Windows Server. One VM is playing image of IBM Infosphere Streams (3.2) QuickStart Edition and Other MessageSight(1.1) Virtual Appliance.
When using MQTTSource Operator I get following compilation error
1. "make: *** No rule to make target `/home/streamsadmin/sdk/clients/c/include/MQTTAsync.h', needed by `build/operator/mqttStream.o'. Stop.
2. CDISP0141E ERROR: The compilation of the generated code failed."
The sdk path is the SDK of IBM MessageSight. I am trying to connetc streams with MessageSight using MQTT operator. Is the problem with SDK or with my code? Please find the code below.
composite MQTTtestApp {
graph
(stream<blob demoData> mqttStream;stream<rstring errorMessage> myErrorStream) = MQTTSource()
{
param
serverURI : "192.168.206.130:1883";
topics : ["DemoMessagingPolicy"];
format: block;
output
myErrorStream : errorMessage = getError();
}
stream<rstring dataSchema> ParsedMsg = Parse(mqttStream)
{
param
format :csv;
}
() as myMessageSink = FileSink(ParsedMsg)
{
param
file : "data.csv";
format : csv;
}
In this version of the operator, you will need to do the following to get the code to compile:
1) Download the MQTT client and have it installed on the VM. See this link for details: http://www-01.ibm.com/support/knowledgecenter/SSCRJU_3.2.0/com.ibm.swg.im.infosphere.streams.messaging-toolkit.doc/doc/msgtoolkit-reqs.html?lang=en
2) Set he STREAMS_MESSAGING_MQTT_HOME environment variable. This environment should point to the install location of the MQTT client
There is a newer version of the MQTT operators that is easier to set up. In the new version, the MQTT client is included as part of the package. Therefore, you will no longer need to install the client separately, or set the environment variable.
See this project for details.
http://ibmstreams.github.io/streamsx.messaging/

Wirecloud, IDM Object Storage GE - MultiTenancy

The question pertains to the level of integration of Wirecloud into IDM and Object Storage, when it comes to getting access to shared Containers. Specifically, from a private WC instance running on FI-LAB and having integrated with FI-LAB IDM using the url http://cloud.lab.fi-ware.org/keystone/v2.0 as a keystone endpoint, I seem to be unable to retrieve all the available tenants from IDM (i just get a single one, being the user logged into from WC - say TENANT-B):
{"tenants":[{"enabled":true,"id":"0000000000000000000000000000EFGH","name":"TENANT-B"}]}
Of course, i can see that when logging into FI-LAB from the portal, the answer i get when calling http://cloud.lab.fi-ware.org/keystone/v2.0/tenants is correct:
{"tenants":[{"enabled":true,"id":"0000000000000000000000000000ABCD","name":"TENANT-A"},{"enabled":true,"id":"0000000000000000000000000000EFGH","name":"TENANT-B"}]}
I am trying to get the tenants using the keystone.getTenant({... options ...}) call:
keystone = new KeystoneAPI(keystone_url, {
use_user_fiware_token : true
});
keystone.getTenants({
onSuccess : onGetTenants,
onFailure : function() {
alert("Could not get a valid tenant list");
}
});
Is multitenancy not supported natively on WC or am I missing something?
Seems to be working now, take into account that the IdM and the Open Stack integration has changed.

HTML 5 Geo Location Prompt in Chrome

Just starting to get into HTML 5 and an testing out geo location...liking it so far. I am hitting a bit of a speed bump though...when I try to get my geo location, chrome automatically blocks the page from getting my location. This does not happen at other sites such as the site below:
http://html5demos.com/geo
The scripts I'm using:
<script type="text/javascript" JavaScript" SRC="geo.js"></script>
<script type="text/javascript" JavaScript" SRC="Utility.js"></script>
<script type="text/javascript" JavaScript" SRC="jquery.js"></script>
<script type="text/javascript" JavaScript" SRC="modernizr.js"></script>
function get_location() {
if (geo_position_js.init()) {
geo_position_js.getCurrentPosition(show_map, handle_error);
}
}
function show_map(position) {
var latitude = position.coords.latitude;
var longitude = position.coords.longitude;
alert("lat:" + latitude + " long:" + longitude);
}
function handle_error(err) {
alert(err.code);
if (err.code == 1) {
// user said no!
}
}
if (navigator.geolocation) {
navigator.geolocation.getCurrentPosition(show_map, handle_error);
} else {
error('not supported');
}
I am testing this out from a local directory on my machine, so there isn't really a "domain" like "http://whatever.com/mytestpage.html". Is this why I am not getting prompted? If so, is it possible to force the browswer to request permission to get the user's geo location and is it possible in my scenario?
There's some sort of security restriction in place in Chrome for using geolocation from a file:/// URI, though unfortunately it doesn't seem to record any errors to indicate that. It will work from a local web server. If you have python installed try opening a command prompt in the directory where your test files are and issuing the command:
python -m SimpleHTTPServer
It should start up a web server on port 8000 (might be something else, but it'll tell you in the console what port it's listening on), then browse to http://localhost:8000/mytestpage.html
If you don't have python there are equivalent modules in Ruby, or Visual Web Developer Express comes with a built in local web server.
None of the above helped me.
After a little research I found that as of M50 (April 2016) - Chrome now requires a secure origin (such as HTTPS) for Geolocation.
Deprecated Features on Insecure Origins
The host "localhost" is special b/c its "potentially secure". You may not see errors during development if you are deploying to your development machine.
As already mentioned in the answer by robertc, Chrome blocks certain functionality, like the geo location with local files. An easier alternative to setting up an own web server would be to just start Chrome with the parameter --allow-file-access-from-files. Then you can use the geo location, provided you didn't turn it off in your settings.
The easiest way is to click on the area left to the address bar and change location settings there. It allows to set location options even for file:///
Make sure it's not blocked at your settings
http://www.howtogeek.com/howto/16404/how-to-disable-the-new-geolocation-feature-in-google-chrome/
if you're hosting behind a server, and still facing issues:
try changing localhost to 127.0.0.1 e.g. http://localhost:8080/ to http://127.0.0.1:8080/
The issue I was facing was that I was serving a site using apache tomcat within an eclipse IDE (eclipse luna).
For my sanity check I was using Remy Sharp's demo:
https://github.com/remy/html5demos/blob/eae156ca2e35efbc648c381222fac20d821df494/demos/geo.html
and was getting the error after making minor tweaks to the error function despite hosting the code on the server (was only working on firefox and failing on chrome and safari):
"User denied Geolocation"
I made the following change to get more detailed error message:
function error(msg) {
var s = document.querySelector('#status');
msg = msg.message ? msg.message : msg; //add this line
s.innerHTML = typeof msg == 'string' ? msg : "failed";
s.className = 'fail';
// console.log(arguments);
}
failing on internet explorer behind virtualbox IE10 on http://10.0.2.2:8080 :
"The current location cannot be determined"
For an easy workaround, just copy the HTML file to some cloud share, such as Dropbox, and use the shared link in your browser. Easy.
I too had this problem when i was trying out Gelocation API. I then started IIS express through visual studio and then accessed the page and It worked without any issue in all browsers.
Check Google Chrome setting and permit location access
Change your default location settings.
On your computer, open Chrome.
At the top right, click More Settings.
Under "Privacy and security," click Site settings.
Click Location.
Turn Ask before accessing on or off.
After I changed those settings, Geolocation worked for me.