Skip to content
GitLab
Projects
Groups
Snippets
Help
Loading...
Help
What's new
7
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Sign in
Toggle navigation
Open sidebar
Coscine
B
backend
apis
Project
Commits
e21dbddb
Commit
e21dbddb
authored
Jul 04, 2019
by
Benedikt Heinrichs
1
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
New: Implement ProjectController
parent
ad8919d3
Changes
20
Pipelines
1
Hide whitespace changes
Inline
Side-by-side
Showing
20 changed files
with
641 additions
and
34 deletions
+641
-34
src/Project.Tests/Project.Tests.csproj
src/Project.Tests/Project.Tests.csproj
+1
-1
src/Project.Tests/ProjectControllerTests.cs
src/Project.Tests/ProjectControllerTests.cs
+1
-6
src/Project/Authenticator.cs
src/Project/Authenticator.cs
+37
-4
src/Project/Configurator.cs
src/Project/Configurator.cs
+1
-1
src/Project/Controllers/ProjectController.cs
src/Project/Controllers/ProjectController.cs
+66
-8
src/Project/DatabaseConnection.cs
src/Project/DatabaseConnection.cs
+58
-0
src/Project/Exceptions/InvalidTokenException.cs
src/Project/Exceptions/InvalidTokenException.cs
+15
-0
src/Project/Exceptions/NotAuthorizedException.cs
src/Project/Exceptions/NotAuthorizedException.cs
+15
-0
src/Project/Factories/ProjectFactory.cs
src/Project/Factories/ProjectFactory.cs
+41
-0
src/Project/JWTHandler.cs
src/Project/JWTHandler.cs
+64
-0
src/Project/Models/DatabaseModel.cs
src/Project/Models/DatabaseModel.cs
+85
-0
src/Project/Models/ProjectModel.cs
src/Project/Models/ProjectModel.cs
+82
-0
src/Project/Models/ResourceModel.cs
src/Project/Models/ResourceModel.cs
+41
-0
src/Project/Models/RoleModel.cs
src/Project/Models/RoleModel.cs
+29
-0
src/Project/Models/User.cs
src/Project/Models/User.cs
+0
-6
src/Project/Models/UserModel.cs
src/Project/Models/UserModel.cs
+26
-0
src/Project/Program.cs
src/Project/Program.cs
+7
-6
src/Project/Project.csproj
src/Project/Project.csproj
+36
-2
src/Project/ReturnObjects/ProjectObject.cs
src/Project/ReturnObjects/ProjectObject.cs
+28
-0
src/Project/packages.config
src/Project/packages.config
+8
-0
No files found.
src/Project.Tests/Project.Tests.csproj
View file @
e21dbddb
...
...
@@ -229,7 +229,7 @@
<Reference
Include=
"System.Xml"
/>
</ItemGroup>
<ItemGroup>
<Compile
Include=
"
Home
ControllerTests.cs"
/>
<Compile
Include=
"
Project
ControllerTests.cs"
/>
<Compile
Include=
"Properties\AssemblyInfo.cs"
/>
</ItemGroup>
<ItemGroup>
...
...
src/Project.Tests/
Home
ControllerTests.cs
→
src/Project.Tests/
Project
ControllerTests.cs
View file @
e21dbddb
...
...
@@ -7,15 +7,10 @@ namespace Coscine.Api.Project.Tests
{
[
TestFixture
]
public
class
Home
ControllerTests
public
class
Project
ControllerTests
{
private
readonly
ProjectController
_projectController
=
new
ProjectController
();
[
Test
]
public
void
GreetTest
()
{
}
[
Test
]
public
void
IndexTest
()
{
...
...
src/Project/Authenticator.cs
View file @
e21dbddb
using
Microsoft.AspNetCore.Mvc
;
using
Coscine.Api.Project.Models
;
using
Coscine.Database.Model
;
using
Microsoft.AspNetCore.Mvc
;
using
System
;
using
System.Collections.Generic
;
using
System.Linq
;
...
...
@@ -17,14 +19,45 @@ namespace Coscine.Api.Project
}
public
bool
ValidUser
()
{
try
{
GetUserFromToken
();
}
catch
(
Exception
)
{
return
false
;
}
return
true
;
}
public
User
GetUserFromToken
()
{
var
bearer
=
_controller
.
Request
.
Headers
[
"bearer"
];
if
(!
string
.
IsNullOrWhiteSpace
(
bearer
))
{
// Todo: Validate User
return
true
;
JWTHandler
jwtHandler
=
new
JWTHandler
(
Program
.
Configurator
.
Configuration
);
var
claims
=
jwtHandler
.
GetContents
(
bearer
);
var
userClaim
=
(
from
claimObj
in
claims
where
claimObj
.
Type
==
"UserId"
select
claimObj
).
First
();
UserModel
userModel
=
new
UserModel
();
return
userModel
.
GetById
(
Guid
.
Parse
(
userClaim
.
Value
));
}
return
false
;
else
{
throw
new
ArgumentException
(
"Bearer Token is not set!"
);
}
}
public
void
ValidateAndExecute
(
Action
<
User
>
action
)
{
action
.
Invoke
(
GetUserFromToken
());
}
public
T
ValidateAndExecute
<
T
>(
Func
<
User
,
T
>
func
)
{
return
func
.
Invoke
(
GetUserFromToken
());
}
// Todo: Add roles as parameter
...
...
src/Project/Configurator.cs
View file @
e21dbddb
...
...
@@ -5,7 +5,7 @@ using System.Net.NetworkInformation;
namespace
Coscine.Api.Project
{
class
Configurator
public
class
Configurator
{
public
ApplicationInformation
ApplicationInformation
{
get
;
set
;
}
=
new
ApplicationInformation
();
public
IConfiguration
Configuration
{
get
;
set
;
}
...
...
src/Project/Controllers/ProjectController.cs
View file @
e21dbddb
using
Microsoft.AspNetCore.Mvc
;
using
Coscine.Api.Project.Exceptions
;
using
Coscine.Api.Project.Factories
;
using
Coscine.Api.Project.Models
;
using
Coscine.Api.Project.ReturnObjects
;
using
Microsoft.AspNetCore.Mvc
;
using
System
;
using
System.Linq
;
namespace
Coscine.Api.Project.Controllers
{
...
...
@@ -14,33 +20,85 @@ namespace Coscine.Api.Project.Controllers
[
Route
(
"[controller]"
)]
public
IActionResult
Index
()
{
return
Ok
(
"Hello World from a controller"
);
return
Ok
(
_authenticator
.
ValidateAndExecute
((
user
)
=>
{
ProjectModel
projectModel
=
new
ProjectModel
();
return
projectModel
.
GetAllWhere
((
project
)
=>
{
return
(
from
projectRole
in
project
.
ProjectRolesProjectIdIds
where
projectRole
.
User
==
user
&&
projectRole
.
Role
.
DisplayName
==
"Owner"
select
projectRole
).
Any
();
}).
Select
((
project
)
=>
{
return
new
ProjectObject
(
project
.
Id
,
project
.
Description
,
project
.
DisplayName
,
project
.
Organization
);
});
}));
}
//[Route("[controller]/greet/{username}")] would also work, but would take all commands
[
HttpGet
(
"[controller]/{id}"
)]
public
IActionResult
Get
(
string
id
)
{
return
Ok
(
id
);
return
Ok
(
_authenticator
.
ValidateAndExecute
((
user
)
=>
{
ProjectModel
projectModel
=
new
ProjectModel
();
var
project
=
projectModel
.
GetById
(
Guid
.
Parse
(
id
));
return
new
ProjectObject
(
project
.
Id
,
project
.
Description
,
project
.
DisplayName
,
project
.
Organization
);
}));
}
//[Route("[controller]/greet/{username}")] would also work, but would take all commands
[
HttpPost
(
"[controller]/{id}"
)]
public
IActionResult
Update
(
string
id
)
{
return
Ok
(
id
);
return
Ok
(
_authenticator
.
ValidateAndExecute
((
user
)
=>
{
ProjectObject
projectObject
=
ObjectFactory
<
ProjectObject
>.
DeserializeFromStream
(
Request
.
Body
);
ProjectModel
projectModel
=
new
ProjectModel
();
var
project
=
projectModel
.
GetById
(
Guid
.
Parse
(
id
));
if
(
projectModel
.
OwnsProject
(
user
,
project
))
{
return
projectModel
.
Update
(
project
);
}
else
{
throw
new
NotAuthorizedException
(
"The user is not authorized to perform an update on the selected project"
);
}
}));
}
[
HttpP
u
t
(
"[controller]"
)]
[
HttpP
os
t
(
"[controller]"
)]
public
IActionResult
Store
()
{
return
Ok
();
return
Ok
(
_authenticator
.
ValidateAndExecute
((
user
)
=>
{
ProjectObject
projectObject
=
ObjectFactory
<
ProjectObject
>.
DeserializeFromStream
(
Request
.
Body
);
ProjectModel
projectModel
=
new
ProjectModel
();
var
project
=
projectModel
.
StoreFromObject
(
projectObject
,
user
);
return
new
ProjectObject
(
project
.
Id
,
project
.
Description
,
project
.
DisplayName
,
project
.
Organization
);
}));
}
[
HttpP
u
t
(
"[controller]/{id}/resource/{resource_id}"
)]
[
HttpP
os
t
(
"[controller]/{id}/resource/{resource_id}"
)]
public
IActionResult
AddResource
(
string
id
,
string
resource_id
)
{
return
Ok
(
id
);
return
Ok
(
_authenticator
.
ValidateAndExecute
((
user
)
=>
{
ProjectModel
projectModel
=
new
ProjectModel
();
var
project
=
projectModel
.
GetById
(
Guid
.
Parse
(
id
));
ResourceModel
resourceModel
=
new
ResourceModel
();
var
resource
=
resourceModel
.
GetById
(
Guid
.
Parse
(
resource_id
));
if
(
projectModel
.
OwnsProject
(
user
,
project
)
&&
resourceModel
.
OwnsResource
(
user
,
resource
))
{
projectModel
.
AddResource
(
project
,
resource
);
return
true
;
}
else
{
throw
new
NotAuthorizedException
(
"User is not authorized to add resource to project!"
);
}
}));
}
}
}
src/Project/DatabaseConnection.cs
0 → 100644
View file @
e21dbddb
using
Coscine.Configuration
;
using
Coscine.Database.Model
;
using
System
;
using
System.Collections.Generic
;
using
System.Linq
;
using
System.Text
;
using
System.Threading.Tasks
;
namespace
Coscine.Api.Project
{
public
class
DatabaseConnection
{
private
IConfiguration
_configuration
;
public
DatabaseConnection
(
IConfiguration
configuration
)
{
_configuration
=
configuration
;
}
private
const
string
DbDataSourceKey
=
"coscine/global/db_data_source"
;
private
const
string
DbNameKey
=
"coscine/global/db_name"
;
private
const
string
DbUserIdKey
=
"coscine/global/db_user_id"
;
private
const
string
DbPasswordKey
=
"coscine/global/db_password"
;
private
string
GetDbConnectionString
()
{
var
dbDataSource
=
_configuration
.
GetString
(
DbDataSourceKey
);
var
dbDatabase
=
_configuration
.
GetString
(
DbNameKey
);
var
dbUserId
=
_configuration
.
GetString
(
DbUserIdKey
);
var
dbPassword
=
_configuration
.
GetString
(
DbPasswordKey
);
return
$"Data Source=
{
dbDataSource
}
; Database=
{
dbDatabase
}
; User Id=
{
dbUserId
}
; Password=
{
dbPassword
}
;"
;
}
private
string
GetProviderName
()
{
return
"SqlServer.2008"
;
}
public
void
ConnectToDatabase
(
Action
<
CoscineDB
>
action
)
{
using
(
var
coscineDB
=
new
CoscineDB
(
GetProviderName
(),
GetDbConnectionString
()))
{
action
.
Invoke
(
coscineDB
);
}
}
public
T
ConnectToDatabase
<
T
>(
Func
<
CoscineDB
,
T
>
func
)
{
T
result
;
using
(
var
coscineDB
=
new
CoscineDB
(
GetProviderName
(),
GetDbConnectionString
()))
{
result
=
func
.
Invoke
(
coscineDB
);
}
return
result
;
}
}
}
src/Project/
Models/Project
.cs
→
src/Project/
Exceptions/InvalidTokenException
.cs
View file @
e21dbddb
...
...
@@ -4,16 +4,12 @@ using System.Linq;
using
System.Text
;
using
System.Threading.Tasks
;
namespace
Coscine.Api.Project.
Model
s
namespace
Coscine.Api.Project.
Exception
s
{
public
class
Project
public
class
InvalidTokenException
:
Exception
{
// TODO: Implement checking
public
bool
OwnsProject
(
User
user
)
public
InvalidTokenException
(
string
message
)
:
base
(
message
)
{
return
true
;
}
}
}
src/Project/Exceptions/NotAuthorizedException.cs
0 → 100644
View file @
e21dbddb
using
System
;
using
System.Collections.Generic
;
using
System.Linq
;
using
System.Text
;
using
System.Threading.Tasks
;
namespace
Coscine.Api.Project.Exceptions
{
public
class
NotAuthorizedException
:
Exception
{
public
NotAuthorizedException
(
string
message
)
:
base
(
message
)
{
}
}
}
src/Project/Factories/ProjectFactory.cs
0 → 100644
View file @
e21dbddb
using
System
;
using
System.Collections.Generic
;
using
System.IO
;
using
System.Linq
;
using
System.Runtime.Serialization
;
using
System.Runtime.Serialization.Formatters.Binary
;
using
System.Text
;
using
System.Threading.Tasks
;
using
Coscine.Api.Project.ReturnObjects
;
namespace
Coscine.Api.Project.Factories
{
public
class
ObjectFactory
<
T
>
{
public
static
MemoryStream
SerializeToStream
(
T
o
)
{
MemoryStream
stream
=
new
MemoryStream
();
IFormatter
formatter
=
new
BinaryFormatter
();
formatter
.
Serialize
(
stream
,
o
);
return
stream
;
}
public
static
T
DeserializeFromStream
(
MemoryStream
stream
)
{
IFormatter
formatter
=
new
BinaryFormatter
();
stream
.
Seek
(
0
,
SeekOrigin
.
Begin
);
T
o
=
(
T
)
formatter
.
Deserialize
(
stream
);
return
o
;
}
public
static
T
DeserializeFromStream
(
Stream
body
)
{
MemoryStream
memoryStream
=
new
MemoryStream
();
body
.
CopyTo
(
memoryStream
);
T
o
=
DeserializeFromStream
(
memoryStream
);
memoryStream
.
Close
();
return
o
;
}
}
}
src/Project/JWTHandler.cs
0 → 100644
View file @
e21dbddb
using
Coscine.Api.Project.Exceptions
;
using
Coscine.Configuration
;
using
Microsoft.IdentityModel.Tokens
;
using
System
;
using
System.Collections.Generic
;
using
System.IdentityModel.Tokens.Jwt
;
using
System.Linq
;
using
System.Security.Claims
;
using
System.Text
;
using
System.Threading.Tasks
;
namespace
Coscine.Api.Project
{
public
class
JWTHandler
{
private
readonly
IConfiguration
_configuration
;
private
readonly
JwtSecurityTokenHandler
_jwtSecurityTokenHandler
;
public
JWTHandler
(
IConfiguration
configuration
)
{
_configuration
=
configuration
;
_jwtSecurityTokenHandler
=
new
JwtSecurityTokenHandler
();
}
public
bool
ValidToken
(
string
token
)
{
string
secretKey
=
_configuration
.
GetString
(
"coscine/global/jwtsecret"
);
if
(
secretKey
==
null
)
{
throw
new
ArgumentNullException
(
"JWT Secret Configuration value is not set!"
);
}
var
securityKey
=
new
SymmetricSecurityKey
(
Encoding
.
UTF8
.
GetBytes
(
secretKey
));
TokenValidationParameters
tokenValidationParameters
=
new
TokenValidationParameters
();
tokenValidationParameters
.
TokenDecryptionKey
=
securityKey
;
try
{
_jwtSecurityTokenHandler
.
ValidateToken
(
token
,
tokenValidationParameters
,
out
SecurityToken
securityToken
);
}
catch
(
Exception
)
{
return
false
;
}
return
true
;
}
public
IEnumerable
<
Claim
>
GetContents
(
string
jwt
)
{
if
(
ValidToken
(
jwt
))
{
var
token
=
_jwtSecurityTokenHandler
.
ReadJwtToken
(
jwt
);
return
token
.
Claims
;
}
else
{
throw
new
InvalidTokenException
(
"Invalid token!"
);
}
}
}
}
src/Project/Models/DatabaseModel.cs
0 → 100644
View file @
e21dbddb
using
Coscine.Configuration
;
using
Coscine.Database.Model
;
using
LinqToDB
;
using
System
;
using
System.Collections.Generic
;
using
System.Linq
;
using
System.Text
;
using
System.Threading.Tasks
;
namespace
Coscine.Api.Project.Models
{
public
abstract
class
DatabaseModel
<
T
>
{
public
DatabaseConnection
DatabaseConnection
{
get
;
set
;
}
public
DatabaseModel
(
IConfiguration
configuration
)
{
DatabaseConnection
=
new
DatabaseConnection
(
configuration
);
}
public
abstract
Guid
GetIdFromObject
(
T
databaseObject
);
public
abstract
ITable
<
T
>
GetITableFromDatabase
(
CoscineDB
db
);
public
T
GetById
(
Guid
id
)
{
return
DatabaseConnection
.
ConnectToDatabase
((
db
)
=>
{
return
(
from
tableEntry
in
GetITableFromDatabase
(
db
)
where
GetIdFromObject
(
tableEntry
)
==
id
select
tableEntry
).
First
();
});
}
public
T
GetWhere
(
Func
<
T
,
bool
>
whereClause
)
{
return
DatabaseConnection
.
ConnectToDatabase
((
db
)
=>
{
return
(
from
tableEntry
in
GetITableFromDatabase
(
db
)
where
whereClause
.
Invoke
(
tableEntry
)
select
tableEntry
).
First
();
});
}
public
IEnumerable
<
T
>
GetAll
()
{
return
DatabaseConnection
.
ConnectToDatabase
((
db
)
=>
{
return
(
from
tableEntry
in
GetITableFromDatabase
(
db
)
select
tableEntry
).
ToList
();
});
}
public
IEnumerable
<
T
>
GetAllWhere
(
Func
<
T
,
bool
>
whereClause
)
{
return
DatabaseConnection
.
ConnectToDatabase
((
db
)
=>
{
return
(
from
tableEntry
in
GetITableFromDatabase
(
db
)
where
whereClause
.
Invoke
(
tableEntry
)
select
tableEntry
).
ToList
();
});
}
public
int
Update
(
T
databaseObject
)
{
return
DatabaseConnection
.
ConnectToDatabase
((
db
)
=>
{
return
db
.
Update
(
databaseObject
);
});
}
public
int
Insert
(
T
databaseObject
)
{
return
DatabaseConnection
.
ConnectToDatabase
((
db
)
=>
{
return
db
.
Insert
(
databaseObject
);
});
}
}
}
src/Project/Models/ProjectModel.cs
0 → 100644
View file @
e21dbddb
using
System
;
using
System.Collections.Generic
;
using
System.Linq
;
using
System.Text
;
using
System.Threading.Tasks
;
using
Coscine.Api.Project.Exceptions
;
using
Coscine.Api.Project.ReturnObjects
;
using
Coscine.Database.Model
;
using
LinqToDB
;
namespace
Coscine.Api.Project.Models
{
public
class
ProjectModel
:
DatabaseModel
<
Coscine
.
Database
.
Model
.
Project
>
{
public
ProjectModel
()
:
base
(
Program
.
Configurator
.
Configuration
)
{
}
public
Coscine
.
Database
.
Model
.
Project
StoreFromObject
(
ProjectObject
projectObject
,
User
user
)
{
Coscine
.
Database
.
Model
.
Project
project
=
new
Coscine
.
Database
.
Model
.
Project
()
{
Description
=
projectObject
.
Description
,
DisplayName
=
projectObject
.
DisplayName
,
Organization
=
projectObject
.
Organization
};
Insert
(
project
);
SetOwner
(
project
,
user
);
return
project
;
}
public
void
SetOwner
(
Coscine
.
Database
.
Model
.
Project
project
,
User
user
)
{
project
.
ProjectRolesProjectIdIds
.
Append
(
new
ProjectRole
()
{
Project
=
project
,
User
=
user
,
Role
=
new
RoleModel
().
GetWhere
((
role
)
=>
{
return
role
.
DisplayName
==
"Owner"
;
})
});
Update
(
project
);
}
public
bool
OwnsProject
(
User
user
,
Coscine
.
Database
.
Model
.
Project
project
)
{
return
DatabaseConnection
.
ConnectToDatabase
((
db
)
=>
{
return
(
from
relation
in
db
.
ProjectRoles
where
relation
.
Project
==
project
&&
relation
.
User
==
user
&&
relation
.
Role
.
DisplayName
==
"Owner"
select
relation
).
Any
();
});
}
public
void
AddResource
(
Coscine
.
Database
.
Model
.
Project
project
,
Resource
resource
)
{
if
(
project
.
ProjectResourceProjectIdIds
.
Any
((
pr
)
=>
pr
.
Resource
==
resource
))
{
throw
new
InvalidOperationException
(
"Resource is already assigned to project!"
);
}
ProjectResource
projectResource
=
new
ProjectResource
();
projectResource
.
Project
=
project
;
projectResource
.
Resource
=
resource
;
project
.
ProjectResourceProjectIdIds
.
Append
(
projectResource
);
Update
(
project
);
}
public
override
Guid
GetIdFromObject
(
Database
.
Model
.
Project
databaseObject
)
{
return
databaseObject
.
Id
;
}
public
override
ITable
<
Database
.
Model
.
Project
>
GetITableFromDatabase
(
CoscineDB
db
)
{
return
db
.
Projects
;
}
}
}
src/Project/Models/ResourceModel.cs
0 → 100644
View file @
e21dbddb
using
Coscine.Database.Model
;
using
LinqToDB
;
using
System
;
using
System.Collections.Generic
;
using
System.Linq
;
using
System.Text
;
using
System.Threading.Tasks
;
namespace
Coscine.Api.Project.Models
{
public
class
ResourceModel
:
DatabaseModel
<
Resource
>
{
public
ResourceModel
()
:
base
(
Program
.
Configurator
.
Configuration
)
{
}
public
bool
OwnsResource
(
User
user
,
Resource
resource
)
{
return
DatabaseConnection
.
ConnectToDatabase
((
db
)
=>
{
return
(
from
relation
in
db
.
ProjectRoles
where
relation
.
User
==
user
&&
relation
.
Role
.
DisplayName
==
"Owner"
&&
relation
.
Project
.
ProjectResourceProjectIdIds
.
Any
((
projectResource
)
=>
projectResource
.
Resource
==
resource
)
select
relation
).
Any
();
});
}
public
override
Guid
GetIdFromObject
(
Resource
databaseObject
)
{