In our ASP.NET MVC Core app we are using ASP.NET Idenity to implement user management.
Question: Instead of using ASP.NET user interface, how can we directly create a user into the SQL Database (using a SQL statement etc.)? Will creating a user directly in ASPNETUsers table cause any issue? Note: We need to populate built-in identity table ASPNETUsers from a list of users. Password can be anything and no specific role is required.
Here is the insert script for AspNetUsers
INSERT [dbo].[AspNetUsers] ([Id], [AccessFailedCount], [ConcurrencyStamp],
[Email], [EmailConfirmed], [LockoutEnabled], [LockoutEnd], [NormalizedEmail],
[NormalizedUserName], [PasswordHash], [PhoneNumber], [PhoneNumberConfirmed],
[SecurityStamp], [TwoFactorEnabled], [UserName]) VALUES
(N'0633e088-30a6-444f-9603-70d7c26748ef', 0,
N'd2feada1-c7db-4f5a-801c-4ae5c990a49d', N'user#domain.com', 1, 1, NULL,
N'USER#DOMAIN.COM', N'USER#DOMAIN.COM',
N'AQAAAAEAACcQAAAAEBqhdvkH3O3glua9IFU+LDamc3mj03dPQ/8brAW34GTN6kxMOqs5je90FNn7fuNleQ==',
N'+10001234567', 1, N'6123adf0-fc53-4abb-b6a4-52d164da4e4f', 0, N'user#domain.com')
GO
Of course you will need to generate your own Guids and hash your own password.
Related
Where can I find breaking changes list from version 2 and/or 3 to version 4 of IdentityServer4?
I am trying to upgrade a project with IdentityServer4 version 2 to version 4.
I made a migration from 2.2 to 4.1.2 version two years ago and I remember I found some breaking changes. Others were imposed by the upgrade of framework I made (net core 2.1 to 3.1). These are some of the changes related only to IdentityServer4:
Database scheme. If you have data in production you'll need to maintain this data in the migration. Automatic migrations will delete and recreate tables mercilessly. There are table and column renames, new columns, deleted columns, changes in the indexes...
Client Cors Origins validation. There is a new validation to force all Url configured in ClientCorsOrigins to complain with an Origin format. If only one of them does not comply with the format, an exception is thrown. You should review your production values to avoid fails.
// format:
<protocol>://<domain>:<port>
// good examples:
http://localhost:5000
http://example.com
https://anotherdomain.com
http://example.com:1234
// bad examples
http://example.com/
https://example.com/mypath
example.com:1234
Some code changes:
AuthorizationRequest.ClientId -> AuthorizationRequest.Client.ClientId.
ResourceValidationResult groups ApiResources and IdentityResources properties in a common property called Resources.
ValidatedTokenRequest changes his property Scopes to RequestedScopes.
GetAllUserConsentsAsync -> GetAllUserGrantsAsync.
In your UI some ModelViews will need to be updated to the new scheme. If you stared with the QuickStart.UI you can compare with the new version to add the new features.
If you have an admin you'll have to adapt it to the new scheme.
Migrations
I created the migrations automatically and then I edited the migration to reorder and to add manual scripts to save the data (For example, create a table before deleting the old one and move the data).
These are the scripts I had to insert manually for the Up migration.
Reorder the code to create ApiResourceScopes table before deleting column ApiResourceId from ApiScopes table.
Insert Into [ApiResourceScopes] ([ApiResourceId], [Scope]) Select [ApiResourceId], [Name] From [ApiScopes]
As ApiScopes has a new field called Enabled and by default takes 0, you'll want to enable for all of them. Run this script just before create the Enabled column:
Update [ApiScopes] set [Enabled] = 1
ApiSecrets must be moved to the new table ApiResourceSecrets. So you should run this script before delete ApiSecrets:
Insert Into [ApiResourceSecrets] ([Description], [Value], [Expiration], [Type], [ApiResourceId], [Created]) Select [Description], [Value], [Expiration], [Type], [ApiResourceId], GetDate() From [ApiSecrets]
The table IdentityClaims is renamed to IdentityResourceClaims. So you'll need to run this script after crate IdentityResourceClaims and before delete IdentityClaims.
Insert Into [IdentityResourceClaims] ([Type], [IdentityResourceId]) Select [Type], [IdentityResourceId] From [IdentityClaims]
For the Down migration you need to do exactly the reverse:
Restore ApiScopes. Move the data from ApiResourceScopes.ApiResourceId by using in the join the Scope and the Name fields respectively.
Update [ApiScopes] Set [ApiScopes].[ApiResourceId] = apir.[ApiResourceId] from [ApiScopes] apis Inner Join [ApiResourceScopes] apir On apis.[Name] = apir.[Scope]
Restore ApiSecrets. Move the data after create ApiSecrets table and before delete ApiResourceSecrets:
Insert Into [ApiSecrets] ([Description], [Value], [Expiration], [Type], [ApiResourceId]) Select [Description], [Value], [Expiration], [Type], [ApiResourceId] From [ApiResourceSecrets]
Restore IdentityClaims. Move the data after create IdentityClaims and before delete IdentityResourceClaims:
Insert Into [IdentityClaims] ([Type], [IdentityResourceId]) Select [Type], [IdentityResourceId] From [IdentityResourceClaims]
I am trying to load data from a CSV file to a table in my Azure Database following the steps in https://learn.microsoft.com/en-us/sql/t-sql/statements/bulk-insert-transact-sql?view=sql-server-ver15#f-importing-data-from-a-file-in-azure-blob-storage, using the Managed Identity option. When I run the query, I receive this error:
Failed to execute query. Error: Referenced external data source "adfst" not found.
This is the name of the container I created within my storage account. I have also tried using my storage account, with the same error. Reviewing https://learn.microsoft.com/en-us/sql/relational-databases/import-export/examples-of-bulk-access-to-data-in-azure-blob-storage?view=sql-server-ver15 does not provide any further insight as to what may be causing the issue. My storage account does not have public (anonymous) access configured.
I'm assuming that I'm missing a simple item that would resolve this issue, but I can't figure out what it is. My SQL query is below, modified to not include content that should not be required.
CREATE MASTER KEY ENCRYPTION BY PASSWORD = '**************';
GO
CREATE DATABASE SCOPED CREDENTIAL msi_cred WITH IDENTITY = '***********************';
CREATE EXTERNAL DATA SOURCE adfst
WITH ( TYPE = BLOB_STORAGE,
LOCATION = 'https://**********.blob.core.windows.net/adfst'
, CREDENTIAL= msi_cred
);
BULK INSERT [dbo].[Adventures]
FROM 'Startracker_scenarios.csv'
WITH (DATA_SOURCE = 'adfst');
If you want to use Managed Identity to access Azure Blob storage when you run BULK INSERT command. You need to enable Managed Identity for the SQL server. Otherwise, you will get the error Referenced external data source "***" not found. Besides, you also need to assign Storage Blob Data Contributor to the MSI. If you do not do that, you cannot access the CVS file storing in Azure blob
For example
Enable Managed Identity for the SQL server
Connect-AzAccount
#Enable MSI for SQL Server
Set-AzSqlServer -ResourceGroupName your-database-server-resourceGroup -ServerName your-SQL-servername -AssignIdentity
Assign role via Azure Portal
Under your storage account, navigate to Access Control (IAM), and select Add role assignment. Assign Storage Blob Data Contributor RBAC role to the server which you've registered with Azure Active Directory (AAD)
Test
a. Data
1,James,Smith,19750101
2,Meggie,Smith,19790122
3,Robert,Smith,20071101
4,Alex,Smith,20040202
b. script
CREATE TABLE CSVTest
(ID INT,
FirstName VARCHAR(40),
LastName VARCHAR(40),
BirthDate SMALLDATETIME)
GO
CREATE MASTER KEY ENCRYPTION BY PASSWORD = 'YourStrongPassword1';
GO
--> Change to using Managed Identity instead of SAS key
CREATE DATABASE SCOPED CREDENTIAL msi_cred WITH IDENTITY = 'Managed Identity';
GO
CREATE EXTERNAL DATA SOURCE MyAzureBlobStorage
WITH ( TYPE = BLOB_STORAGE,
LOCATION = 'https://jimtestdiag417.blob.core.windows.net/test'
, CREDENTIAL= msi_cred
);
GO
BULK INSERT CSVTest
FROM 'mydata.csv'
WITH (
FIELDTERMINATOR = ',',
ROWTERMINATOR = '\n',
DATA_SOURCE = 'MyAzureBlobStorage');
GO
select * from CSVTest;
GO
I'm currently using a free DB2 warehouse on cloud provided by IBM. What I'm trying to do is to create a new table in the database. However, an error message pops up saying that
To resolve this, I open the web console and run the following command: create tablespace mytablespace pagesize 4096. Then, another error message pops up:
Based on what I have googled, it looks like I need to grant administrator role for the user "DASH******". So I do this by adding an optional parameter to the credentials:
But it doesn't work. Is there any way to workaround this?
EDIT1: I create the table using the following command:
Users are not allowed to create their own tablespaces in free DB2WoC systems, since they don't have the SYSCTRL or SYSADM authorities there. You have to use existing tablespaces where you are allowed to create your tables.
Run the following statement from your DASH*** user.
This statement returns all the tablespaces, where your user is allowed to create tables.
If it doesn't return any rows, then this means, that you should open a ticket to the IBM support. Support should create it for you and grant your user the USE privilege on this tablespace.
SELECT
T.DATATYPE
--, P.PRIVILEGE
--, P.OBJECTTYPE
--, P.OBJECTSCHEMA
, P.OBJECTNAME
, U.AUTHID, U.AUTHIDTYPE
FROM SYSIBMADM.PRIVILEGES P
CROSS JOIN TABLE(VALUES USER) A (AUTHID)
JOIN TABLE (
SELECT GROUP, 'G' FROM table(AUTH_LIST_GROUPS_FOR_AUTHID(A.AUTHID))
UNION ALL
select ROLENAME, 'R' from table(AUTH_LIST_ROLES_FOR_AUTHID(A.AUTHID, 'U'))
UNION ALL
SELECT * FROM TABLE(VALUES ('PUBLIC', 'G'), (A.AUTHID, 'U')) T (AUTHID, AUTHIDTYPE)
) U (AUTHID, AUTHIDTYPE) ON U.AUTHID=P.AUTHID AND U.AUTHIDTYPE=P.AUTHIDTYPE
JOIN SYSCAT.TABLESPACES T ON T.TBSPACE=P.OBJECTNAME
WHERE P.OBJECTTYPE='TABLESPACE' AND T.DATATYPE IN ('A', 'L')
I have a Spring Boot application and would like to seed the database the first time the application runs, but not every time the application runs, and then only if the data does not already exist.
My application has a data.sql file and I have it inserting the default users:
-- insert the administrator
INSERT INTO users(id, username, password_hash, email, first_name, last_name) VALUES
(1, 'admin', 'comixed', 'email1#domain.com', 'ComixEd', 'Administrator'),
(2, 'user', 'comixeduser', 'email2#domain.com', 'ComixEd', 'User')
;
-- insert the supported roles
INSERT INTO roles(id, name) VALUES
(1, 'Administrator'),
(2, 'User')
;
-- set the administrator roles
INSERT INTO users_roles(user_id, role_id) VALUES
(1, 1),
(1, 2),
(2, 2)
;
But Spring is obviously trying to run this file every time I start the app. And when it does an exception is raised since the users and roles are already in the database.
What's a better way to do this? And, optionally, what's a way to add new seed data if, in future, new features require new roles, etc.?
Flyway is what you are looking for https://flywaydb.org/
It is a database migration tool that can be used to create and modify databases in a project. It creates its own table in your schema and adds the script name and a checksum value into the tables. During application boot it scans the scripts, checks to see if they're in the table and if the checksums match still. This makes sure the files don't change and everything has been migrated.
You have to configure it in the application.properties file.
Add this line and it should work as you wish:
spring.jpa.hibernate.ddl-auto = update
I created an asp portal for my customers. They all access the same website and pass in a tokenid, which is a guid. This guid tells me what company they belong to and what they have access to.
I have the membership provider set up to not allow duplicate email addresses and everyone under the same application. So, with this in mind, I figured I could do the following to allow them to register with more than one company with the same email account.
Create an membership provider application for each tokens (for each company).
Write a script that finds all of the accounts that are based on this guid and place them under appropriate application
Will this work? Will it allow my customers to create a login for each token/company using the same email address?
Thanks for the help!
If you script out
[dbo].[aspnet_Membership_FindUsersByEmail]
, you'll see (the default implementation) is already "separated by application". (because this procedure takes "ApplicationName" as a parameter.
So if you programmatically set the
MembershipProvider.ApplicationName
http://msdn.microsoft.com/en-us/library/system.web.security.membershipprovider.applicationname.aspx
Then you should be able to do what you want.
Here is the signature of the procedure mentioned above:
ALTER PROCEDURE [dbo].[aspnet_Membership_FindUsersByEmail]
#ApplicationName nvarchar(256),
#EmailToMatch nvarchar(256),
#PageIndex int,
#PageSize int
AS
REMINDER:
You do not deal with the stored procedures directly. You use the API of the MembershipProvider.
But here is the simple test.
MembershipProvider mp1 = Membership.Providers["App1"];
mp1.CreateUser (.................. )
MembershipProvider mp2 = Membership.Providers["App2"];
mp2.CreateUser (.................. ) /* use same email */
Now, I think you'll have to define each MembershipProvider (and its name) in your config file.
But here is an MSDN link:
http://msdn.microsoft.com/en-us/library/system.web.security.membershipprovidercollection.item.aspx