Skip to content

Commit

Permalink
0.12.1
Browse files Browse the repository at this point in the history
  • Loading branch information
CypherPotato committed May 2, 2023
1 parent 80e9368 commit 54b0a85
Show file tree
Hide file tree
Showing 20 changed files with 839 additions and 110 deletions.
54 changes: 43 additions & 11 deletions .nuget/README.md
Original file line number Diff line number Diff line change
@@ -1,21 +1,53 @@
Sisk is a powerful framework for building powerful web applications for Windows, Linux and Mac. With Sisk, you can use the full power of .NET to create fast, dynamic and poweful web applications. It's an alternative to Microsoft's ASP.NET Core, which it's simpler and easy to understand and control.
# Welcome to Sisk

## Sisk is a powerful framework for building powerful web applications for Windows, Linux and Mac.

With Sisk, you can use the full power of .NET to create fast, dynamic and powerful web applications. It's an alternative to Microsoft's ASP.NET Core, which is simpler and easier to understand and setup.

```cs
public class Program
{
static void Main(string[] args)
{
HttpServer http = HttpServer.Emit(
insecureHttpPort: 5555,
out HttpServerConfiguration serverConfig,
out ListeningHost listeningHost,
out Router mainRouter
);

mainRouter += new Route(RouteMethod.Get, "/", request =>
{
return new HttpResponse(200) { Content = new StringContent("Hello, world!") };
});

http.Start();

Console.WriteLine($"HTTP server is listening on {http.ListeningPrefixes[0]}");

Thread.Sleep(-1);
}
}
```

## Main features:

- 100% open source
- Multi-platform and cross-operating system
- Ultra fast response/second average
- Support to operating system's native HTTP interface listener
- Ultra fast asynchronous response/second average
- Uses the operating system's native HTTP interface listener
- Sustainable and maintainable
- Database-agnostic
- Code-pattern-agnostic
- Easy setup
- Same code implementation for *nix, Mac OS and Windows
- Asynchronous request handling
- Middlewares, before and/or after request handlers
- Configurable error handling
- Support to log access/error logs
- Support to log advanced logging with rotating support
- Easy Cross-Origin Resource Sharing setup
- Server Side Events and Web Sockets support
- Multiple listening hosts per service
- Advanced routing system
- Less than 170kb the entire package
- Written in C#

## Documentation

The specification is complete, however, tutorials are yet to come. By the way, you can access the Sisk documentation [here](https://sisk.proj.pw/#/docs/getting-started) or it's specification [here](https://sisk.proj.pw/#/spec/index).

You can also view release change logs [here](https://github.com/sisk-http/docs/blob/master/Changelog.md).
You can learn how to get started with Sisk [here](https://sisk.project-principium.dev/#/docs/getting-started).
40 changes: 25 additions & 15 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -22,39 +22,49 @@ using Sisk.Core.Routing;

namespace myProgram;

class Program
public class Program
{
static void Main(string[] args)
{
Router router = new Router();
HttpServerConfiguration config = new HttpServerConfiguration();
config.ListeningHosts.Add(new ListeningHost("localhost", 5555, router));
HttpServer server = new HttpServer(config);

router.SetRoute(RouteMethod.Get, "/", (req) =>
HttpServer http = HttpServer.Emit(
insecureHttpPort: 5555,
out HttpServerConfiguration serverConfig,
out ListeningHost listeningHost,
out Router mainRouter
);

mainRouter += new Route(RouteMethod.Get, "/", request =>
{
return req.CreateOkResponse("Hello, world!");
return new HttpResponse(200) { Content = new StringContent("Hello, world!") };
});

server.Start();
Thread.Sleep(-1); // prevent hauting
http.Start();

Console.WriteLine($"HTTP server is listening on {http.ListeningPrefixes[0]}");

Thread.Sleep(-1);
}
}
```

## Features

- 100% open source
- Multi-platform and cross-operating system
- Ultra fast response/second average
- Support to operating system's native HTTP interface listener
- Ultra fast asynchronous response/second average
- Uses the operating system's native HTTP interface listener
- Sustainable and maintainable
- Database-agnostic
- Code-pattern-agnostic
- Easy setup
- Same code implementation for *nix, Mac OS and Windows
- Asynchronous request handling
- Middlewares, before and/or after request handlers
- Configurable error handling
- Support to log access/error logs
- Support to log advanced logging with rotating support
- Easy Cross-Origin Resource Sharing setup
- Server Side Events and Web Sockets support
- Multiple listening hosts per service
- Advanced routing system
- Less than 170kb the entire package
- Written in C#

## Documentation
Expand Down
1 change: 1 addition & 0 deletions service/Provider/ConfigParser.cs
Original file line number Diff line number Diff line change
Expand Up @@ -125,6 +125,7 @@ internal static void ParseConfiguration(ServiceProvider prov, bool softReload)

try
{
fac.Bootstrap();
prov.HttpServer.Start();
}
catch (Exception ex)
Expand Down
2 changes: 1 addition & 1 deletion service/Provider/ServiceProvider.cs
Original file line number Diff line number Diff line change
Expand Up @@ -98,7 +98,7 @@ public class ServiceProvider
/// Gets the configured error log stream. This property is inherited from <see cref="ServerConfiguration"/>.
/// </summary>
/// <definition>
/// public TextWriter? ErrorLogs { get; }
/// public TextWriter? ErrorLogs { get; }
/// </definition>
/// <type>
/// Property
Expand Down
13 changes: 12 additions & 1 deletion service/RouterFactory.cs
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,7 @@ public abstract class RouterFactory
public abstract Router BuildRouter();

/// <summary>
/// Method that is called by the Agirax instantiator with the parameters defined in configuration before calling <see cref="BuildRouter()"/>.
/// Method that is called by the service instantiator with the parameters defined in configuration before calling <see cref="BuildRouter()"/>.
/// </summary>
/// <param name="setupParameters">Parameters that are defined in a configuration file.</param>
/// <definition>
Expand All @@ -45,5 +45,16 @@ public abstract class RouterFactory
/// Sisk.Core.Routing
/// </namespace>
public abstract void Setup(NameValueCollection setupParameters);

/// <summary>
/// Method that is called immediately before initializing the service, after all configurations was parsed and set up.
/// </summary>
/// <definition>
/// public abstract void Bootstrap();
/// </definition>
/// <type>
/// Method
/// </type>
public abstract void Bootstrap();
}
}
6 changes: 3 additions & 3 deletions service/Sisk.ServiceProvider.csproj
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@
<GeneratePackageOnBuild>True</GeneratePackageOnBuild>
<Title>Sisk.ServiceProvider</Title>
<PackageId>Sisk.ServiceProvider</PackageId>
<Version>0.11</Version>
<Version>0.12</Version>
<Authors>CypherPotato</Authors>
<Company>Project Principium</Company>
<Product>Sisk.ServiceProvider</Product>
Expand All @@ -19,8 +19,8 @@
<RepositoryUrl>https://github.com/sisk-http/core</RepositoryUrl>
<PackageTags>http-server,http,web framework</PackageTags>
<RepositoryType>git</RepositoryType>
<AssemblyVersion>0.11</AssemblyVersion>
<FileVersion>0.11</FileVersion>
<AssemblyVersion>0.12</AssemblyVersion>
<FileVersion>0.12</FileVersion>
<NeutralLanguage>en</NeutralLanguage>
<PackageLicenseFile>LICENSE.txt</PackageLicenseFile>
<IncludeSymbols>True</IncludeSymbols>
Expand Down
6 changes: 1 addition & 5 deletions src/Entity/MultipartObject.cs
Original file line number Diff line number Diff line change
Expand Up @@ -246,11 +246,7 @@ internal static MultipartObject[] ParseMultipartObjects(HttpRequest req)
throw new InvalidOperationException("No boundary was specified for this multipart form content.");
}

byte[] bodyBytes = req.RawBody.Skip(2).ToArray();
byte[] boundaryBytes = Encoding.ASCII.GetBytes(boundary);
long contentLength = bodyBytes.Length;

int boundaryLength = boundaryBytes.Length;
byte[] boundaryBytes = Encoding.UTF8.GetBytes(boundary);

/////////
// https://stackoverflow.com/questions/9755090/split-a-byte-array-at-a-delimiter
Expand Down
58 changes: 42 additions & 16 deletions src/Http/HttpRequest.cs
Original file line number Diff line number Diff line change
@@ -1,6 +1,10 @@
using Sisk.Core.Entity;
using Sisk.Core.Http.Streams;
using System.Collections.Specialized;
using System.Net;
using System.Net.WebSockets;
using System.Reflection;
using System.Runtime.InteropServices;
using System.Text;
using System.Web;

Expand Down Expand Up @@ -42,6 +46,7 @@ public sealed class HttpRequest
private HttpServerConfiguration contextServerConfiguration;
private HttpListenerResponse listenerResponse;
private HttpListenerRequest listenerRequest;
private HttpListenerContext context;
private byte[]? contentBytes;
internal bool isStreaming;
private HttpRequestEventSource? activeEventSource;
Expand All @@ -52,7 +57,7 @@ internal HttpRequest(
HttpListenerResponse listenerResponse,
HttpServer server,
ListeningHost host,
HttpServerFlags flags)
HttpListenerContext context)
{
this.baseServer = server;
this.contextServerConfiguration = baseServer.ServerConfiguration;
Expand All @@ -61,7 +66,7 @@ internal HttpRequest(
this.hostContext = host;
this.RequestedAt = DateTime.Now;
this.Query = listenerRequest.QueryString;
this.GenerateRequestId(this.RequestedAt.Ticks);
this.RequestId = Guid.NewGuid();

IPAddress requestRealAddress = new IPAddress(listenerRequest.LocalEndPoint.Address.GetAddressBytes());
this.Origin = requestRealAddress;
Expand Down Expand Up @@ -110,23 +115,19 @@ internal HttpRequest(
this.Cookies[key] = WebUtility.UrlDecode(value);
}
}

this.context = context;
}

internal unsafe void GenerateRequestId(long seeder)
#pragma warning disable
~HttpRequest()
{
long seed = DateTime.Now.Ticks;
byte* reqIdBytes = stackalloc byte[16];

for (int i = 0; i < 16; i++)
{
int j = i / 4;
long k = (seed >> j) + (i * 9);
reqIdBytes[i] = (byte)(k & 0xFF);
}

ReadOnlySpan<byte> reqSpan = new ReadOnlySpan<byte>(reqIdBytes, 16);
this.RequestId = new Guid(reqSpan);
this.contentBytes = null;
this.listenerRequest = null;
this.listenerResponse = null;
this.contextServerConfiguration = null;
}
#pragma warning restore

internal void ImportContents(Stream listenerRequest)
{
Expand Down Expand Up @@ -732,7 +733,7 @@ public HttpResponse CreateRedirectResponse(string location, bool permanent)
/// Gets an Event Source interface for this request. Calling this method will put this <see cref="HttpRequest"/> instance in it's
/// event source listening state.
/// </summary>
/// <param name="identifier">Defines an label to the EventStream connection, useful for finding this connection's reference later.</param>
/// <param name="identifier">Optional. Defines an label to the EventStream connection, useful for finding this connection's reference later.</param>
/// <definition>
/// public HttpRequestEventSource GetEventSource(string? identifier = null)
/// </definition>
Expand All @@ -753,6 +754,31 @@ public HttpRequestEventSource GetEventSource(string? identifier = null)
return activeEventSource;
}

/// <summary>
/// Accepts and acquires a websocket for this request. Calling this method will put this <see cref="HttpRequest"/> instance in
/// streaming state.
/// </summary>
/// <param name="subprotocol">Optional. Determines the sub-protocol to plug the websocket in.</param>
/// <param name="identifier">Optional. Defines an label to the Web Socket connection, useful for finding this connection's reference later.</param>
/// <returns></returns>
/// <definition>
/// public HttpWebSocket GetWebSocket(string? subprotocol = null)
/// </definition>
/// <type>
/// Method
/// </type>
/// <exception cref="InvalidOperationException"></exception>
public HttpWebSocket GetWebSocket(string? subprotocol = null, string? identifier = null)
{
if (isStreaming)
{
throw new InvalidOperationException("This HTTP request is already in streaming mode.");
}
isStreaming = true;
var accept = context.AcceptWebSocketAsync(subprotocol).Result;
return new HttpWebSocket(accept, this, identifier);
}

internal long CalcRequestSize()
{
long l = 0;
Expand Down
12 changes: 10 additions & 2 deletions src/Http/HttpResponse.cs
Original file line number Diff line number Diff line change
Expand Up @@ -21,11 +21,19 @@ namespace Sisk.Core.Http
public class HttpResponse
{
internal const byte HTTPRESPONSE_EMPTY = 2;
internal const byte HTTPRESPONSE_EVENTSOURCE_CLOSE = 4;
internal const byte HTTPRESPONSE_STREAM_CLOSE = 4;
internal const byte HTTPRESPONSE_ERROR = 8;
internal const byte HTTPRESPONSE_CLOSE = 16;
internal int CalculedLength = 0;

#pragma warning disable
~HttpResponse()
{
this.Content = null;
this.Headers = null;
}
#pragma warning restore

/// <summary>
/// Gets or sets an custom HTTP status code and description for this HTTP response. If this property ins't null, it will overwrite
/// the <see cref="Status"/> property in this class.
Expand Down Expand Up @@ -67,7 +75,7 @@ public class HttpResponse
/// <namespace>
/// Sisk.Core.Http
/// </namespace>
public NameValueCollection Headers { get; } = new NameValueCollection();
public NameValueCollection Headers { get; private set; } = new NameValueCollection();

/// <summary>
/// Gets or sets the HTTP response body contents.
Expand Down
Loading

0 comments on commit 54b0a85

Please sign in to comment.