mirror of
https://github.com/openfaas/faasd.git
synced 2025-06-19 04:26:34 +00:00
Compare commits
20 Commits
Author | SHA1 | Date | |
---|---|---|---|
68335e2016 | |||
404af1c4d9 | |||
055e57ec5f | |||
6bb1222ebb | |||
599ae5415f | |||
0d74cac072 | |||
c2b802cbf9 | |||
bd0e1d7718 | |||
bfc87ff432 | |||
032716e3e9 | |||
c813b0810b | |||
fb36d2e5aa | |||
038eb91191 | |||
5576382d96 | |||
7ca2621c98 | |||
a154fd1bc0 | |||
6b1e49a2a5 | |||
5344a32472 | |||
e59e3f0cb6 | |||
2adc1350d4 |
4
LICENSE
4
LICENSE
@ -1,6 +1,6 @@
|
||||
For usage of faasd, see: EULA.md
|
||||
License for faasd contributions from OpenFaaS Ltd - 2017, 2029-2024, see: EULA.md
|
||||
|
||||
See below for source code contributions
|
||||
Only third-party contributions to source code are licensed MIT:
|
||||
|
||||
MIT License
|
||||
|
||||
|
37
README.md
37
README.md
@ -121,7 +121,42 @@ View sample pages, reviews and testimonials on Gumroad:
|
||||
|
||||
["Serverless For Everyone Else"](https://openfaas.gumroad.com/l/serverless-for-everyone-else)
|
||||
|
||||
### Deploy faasd
|
||||
### Deploy OpenFaaS Edge (commercial distribution of faasd)
|
||||
|
||||
OpenFaaS Edge is a commercial distribution of faasd, with enhancements and additional features from OpenFaaS Pro. The [OpenFaaS Pro EULA applies](https://github.com/openfaas/faas/blob/master/pro/EULA.md).
|
||||
|
||||
* Upgraded Pro components from OpenFaaS Standard: Gateway, Cron Connector, JetStream Queue Worker and Classic Scale to Zero
|
||||
* Deploy up to 250 functions per installation
|
||||
* Configure private DNS servers
|
||||
* Airgap-friendly with installation bundled in an OCI image
|
||||
* Detailed RAM/CPU metrics for stateful containers, and functions, including Out Of Memory (OOM) events
|
||||
* Multiple namespace support
|
||||
|
||||
This version is intended for resale as part of a wider solution, and to be deployed both into industrial and on-premises environments.
|
||||
|
||||
Individual [GitHub Sponsors of OpenFaaS](https://github.com/sponsors/openfaas) (25 USD / mo and higher) can use OpenFaaS Edge for personal use.
|
||||
|
||||
You can install OpenFaaS Edge with the following script:
|
||||
|
||||
```bash
|
||||
curl -sLSf \
|
||||
https://raw.githubusercontent.com/openfaas/faasd/refs/heads/master/hack/install-edge.sh \
|
||||
-o install-edge.sh && \
|
||||
chmod +x install-edge.sh
|
||||
sudo -E ./install-edge.sh
|
||||
```
|
||||
|
||||
*For an offline installation*
|
||||
|
||||
Copy the OCI bundle and the install-edge.sh script to the remote server.
|
||||
|
||||
Then mirror the various images from docker-compose.yaml into your private registry, and update the references from i.e. `image: ghcr.io/openfaasltd/gateway` to the equivalents in your registry.
|
||||
|
||||
If your system is unable to install apt, yum, or pacman packages, due to limited network access, then set the `SKIP_OS` environment to 1. The list of packages is available in the `install_required_packages` section of the script.
|
||||
|
||||
### Deploy faasd CE
|
||||
|
||||
faasd-ce supports 15 functions and needs a computer with a stable Internet connection to run. There are some restrictions on commercial use, but [individuals and certain small businesses can use it for free](EULA.md).
|
||||
|
||||
The easiest way to deploy faasd is with cloud-init, we give several examples below, and post IaaS platforms will accept "user-data" pasted into their UI, or via their API.
|
||||
|
||||
|
@ -13,7 +13,6 @@ import (
|
||||
"github.com/openfaas/faas-provider/logs"
|
||||
"github.com/openfaas/faas-provider/proxy"
|
||||
"github.com/openfaas/faas-provider/types"
|
||||
"github.com/openfaas/faasd/pkg"
|
||||
faasd "github.com/openfaas/faasd/pkg"
|
||||
"github.com/openfaas/faasd/pkg/cninetwork"
|
||||
faasdlogs "github.com/openfaas/faasd/pkg/logs"
|
||||
@ -30,8 +29,6 @@ func makeProviderCmd() *cobra.Command {
|
||||
Short: "Run the faasd-provider",
|
||||
}
|
||||
|
||||
command.Flags().String("pull-policy", "Always", `Set to "Always" to force a pull of images upon deployment, or "IfNotPresent" to try to use a cached image.`)
|
||||
|
||||
command.RunE = runProviderE
|
||||
command.PreRunE = preRunE
|
||||
|
||||
@ -40,16 +37,6 @@ func makeProviderCmd() *cobra.Command {
|
||||
|
||||
func runProviderE(cmd *cobra.Command, _ []string) error {
|
||||
|
||||
pullPolicy, flagErr := cmd.Flags().GetString("pull-policy")
|
||||
if flagErr != nil {
|
||||
return flagErr
|
||||
}
|
||||
|
||||
alwaysPull := false
|
||||
if pullPolicy == "Always" {
|
||||
alwaysPull = true
|
||||
}
|
||||
|
||||
config, providerConfig, err := config.ReadFromEnv(types.OsEnv{})
|
||||
if err != nil {
|
||||
return err
|
||||
@ -95,6 +82,7 @@ nameserver 8.8.4.4`), workingDirectoryPermission); err != nil {
|
||||
return err
|
||||
}
|
||||
|
||||
alwaysPull := true
|
||||
bootstrapHandlers := types.FaaSHandlers{
|
||||
FunctionProxy: httpHeaderMiddleware(proxy.NewHandlerFunc(*config, invokeResolver, false)),
|
||||
DeleteFunction: httpHeaderMiddleware(handlers.MakeDeleteHandler(client, cni)),
|
||||
@ -104,14 +92,14 @@ nameserver 8.8.4.4`), workingDirectoryPermission); err != nil {
|
||||
ScaleFunction: httpHeaderMiddleware(handlers.MakeReplicaUpdateHandler(client, cni)),
|
||||
UpdateFunction: httpHeaderMiddleware(handlers.MakeUpdateHandler(client, cni, baseUserSecretsPath, alwaysPull)),
|
||||
Health: httpHeaderMiddleware(func(w http.ResponseWriter, r *http.Request) {}),
|
||||
Info: httpHeaderMiddleware(handlers.MakeInfoHandler(pkg.Version, pkg.GitCommit)),
|
||||
Info: httpHeaderMiddleware(handlers.MakeInfoHandler(faasd.Version, faasd.GitCommit)),
|
||||
ListNamespaces: httpHeaderMiddleware(handlers.MakeNamespacesLister(client)),
|
||||
Secrets: httpHeaderMiddleware(handlers.MakeSecretHandler(client.NamespaceService(), baseUserSecretsPath)),
|
||||
Logs: httpHeaderMiddleware(logs.NewLogHandlerFunc(faasdlogs.New(), config.ReadTimeout)),
|
||||
MutateNamespace: httpHeaderMiddleware(handlers.MakeMutateNamespace(client)),
|
||||
}
|
||||
|
||||
log.Printf("Listening on: 0.0.0.0:%d\n", *config.TCPPort)
|
||||
log.Printf("Listening on: 0.0.0.0:%d", *config.TCPPort)
|
||||
bootstrap.Serve(cmd.Context(), &bootstrapHandlers, config)
|
||||
return nil
|
||||
}
|
||||
|
@ -21,7 +21,7 @@ services:
|
||||
# - "127.0.0.1:8222:8222"
|
||||
|
||||
prometheus:
|
||||
image: docker.io/prom/prometheus:v2.49.1
|
||||
image: docker.io/prom/prometheus:v3.0.1
|
||||
# nobody
|
||||
user: "65534"
|
||||
volumes:
|
||||
@ -39,7 +39,7 @@ services:
|
||||
- "127.0.0.1:9090:9090"
|
||||
|
||||
gateway:
|
||||
image: ghcr.io/openfaas/gateway:0.27.9
|
||||
image: ghcr.io/openfaas/gateway:0.27.12
|
||||
environment:
|
||||
- basic_auth=true
|
||||
- functions_provider_url=http://faasd-provider:8081/
|
||||
@ -69,7 +69,7 @@ services:
|
||||
- "8080:8080"
|
||||
|
||||
queue-worker:
|
||||
image: ghcr.io/openfaas/queue-worker:0.14.1
|
||||
image: ghcr.io/openfaas/queue-worker:0.14.2
|
||||
environment:
|
||||
- faas_nats_address=nats
|
||||
- faas_nats_port=4222
|
||||
|
@ -2,7 +2,7 @@
|
||||
Description=faasd-provider
|
||||
|
||||
[Service]
|
||||
MemoryLimit=500M
|
||||
MemoryMax=500M
|
||||
Environment="secret_mount_path={{.SecretMountPath}}"
|
||||
Environment="basic_auth=true"
|
||||
Environment="hosts_dir=/var/lib/faasd"
|
||||
|
@ -3,7 +3,7 @@ Description=faasd
|
||||
After=faasd-provider.service
|
||||
|
||||
[Service]
|
||||
MemoryLimit=500M
|
||||
MemoryMax=500M
|
||||
ExecStart=/usr/local/bin/faasd up
|
||||
Restart=on-failure
|
||||
RestartSec=10s
|
||||
|
99
hack/install-edge.sh
Normal file
99
hack/install-edge.sh
Normal file
@ -0,0 +1,99 @@
|
||||
#!/bin/bash
|
||||
|
||||
set -e # stop on error
|
||||
set -o pipefail
|
||||
|
||||
if [ "$EUID" -ne 0 ]; then
|
||||
echo "Please run as root or with sudo"
|
||||
exit
|
||||
fi
|
||||
|
||||
has_yum() {
|
||||
[ -n "$(command -v yum)" ]
|
||||
}
|
||||
|
||||
has_apt_get() {
|
||||
[ -n "$(command -v apt-get)" ]
|
||||
}
|
||||
|
||||
has_pacman() {
|
||||
[ -n "$(command -v pacman)" ]
|
||||
}
|
||||
|
||||
install_required_packages() {
|
||||
if $(has_apt_get); then
|
||||
# Debian bullseye is missing iptables. Added to required packages
|
||||
# to get it working in raspberry pi. No such known issues in
|
||||
# other distros. Hence, adding only to this block.
|
||||
# reference: https://github.com/openfaas/faasd/pull/237
|
||||
apt-get update -y
|
||||
apt-get install -y curl runc bridge-utils iptables
|
||||
elif $(has_yum); then
|
||||
yum check-update -y
|
||||
yum install -y curl runc iptables-services which
|
||||
elif $(has_pacman); then
|
||||
pacman -Syy
|
||||
pacman -Sy curl runc bridge-utils
|
||||
else
|
||||
fatal "Could not find apt-get, yum, or pacman. Cannot install dependencies on this OS."
|
||||
exit 1
|
||||
fi
|
||||
}
|
||||
|
||||
echo "OpenFaaS Edge (based upon faasd and OpenFaaS Standard)"
|
||||
echo ""
|
||||
echo ""
|
||||
|
||||
echo "1. Installing required OS packages, set SKIP_OS=1 to skip this step"
|
||||
echo ""
|
||||
|
||||
if [ -z "$SKIP_OS" ]; then
|
||||
install_required_packages
|
||||
fi
|
||||
|
||||
echo "2. Downloading OCI image, and installing pre-requisites"
|
||||
echo ""
|
||||
if [ ! -x "$(command -v arkade)" ]; then
|
||||
# For Centos, RHEL, Fedora, Amazon Linux, and Oracle Linux, use BINLOCATION=/usr/bin/
|
||||
|
||||
if $(has_yum); then
|
||||
BINLOCATION=/usr/bin/
|
||||
fi
|
||||
|
||||
curl -sLS https://get.arkade.dev | BINLOCATION=${BINLOCATION} sh
|
||||
fi
|
||||
|
||||
PATH=$PATH:$HOME/.arkade/bin
|
||||
|
||||
tmpdir=$(mktemp -d)
|
||||
|
||||
# Ensure all existing services are stopped when installing over an
|
||||
# existing faasd installation
|
||||
systemctl stop faasd || :
|
||||
systemctl stop faasd-provider || :
|
||||
systemctl stop containerd || :
|
||||
killall -9 containerd-shim-runc-v2 || :
|
||||
killall -9 faasd || :
|
||||
|
||||
# crane, or docker can also be used to download the OCI image and to extract it
|
||||
|
||||
# Rather than the :latest tag, a specific tag can be given
|
||||
# Use "crane ls ghcr.io/openfaasltd/faasd-pro" to see available tags
|
||||
|
||||
${BINLOCATION}arkade oci install --path ${tmpdir} \
|
||||
ghcr.io/openfaasltd/faasd-pro:latest
|
||||
|
||||
cd ${tmpdir}
|
||||
./install.sh ./
|
||||
|
||||
echo ""
|
||||
echo "3. You now need to activate your license via GitHub"
|
||||
echo ""
|
||||
echo "sudo -E faasd github login"
|
||||
echo "sudo -E faasd activate"
|
||||
echo ""
|
||||
echo ""
|
||||
echo "4. Then perform the final installation steps"
|
||||
echo ""
|
||||
echo "sudo -E sh -c \"cd ${tmpdir}/var/lib/faasd && faasd install\""
|
||||
echo ""
|
@ -12,7 +12,7 @@ const (
|
||||
OrchestrationIdentifier = "containerd"
|
||||
|
||||
// ProviderName name of the provider
|
||||
ProviderName = "faasd"
|
||||
ProviderName = "faasd-ce"
|
||||
)
|
||||
|
||||
// MakeInfoHandler creates handler for /system/info endpoint
|
||||
|
@ -96,32 +96,24 @@ func MakeReplicaUpdateHandler(client *containerd.Client, cni gocni.CNI) func(w h
|
||||
|
||||
createNewTask := false
|
||||
|
||||
// Scale to zero
|
||||
if req.Replicas == 0 {
|
||||
// If a task is running, pause it
|
||||
if taskExists && taskStatus.Status == containerd.Running {
|
||||
if pauseErr := task.Pause(ctx); pauseErr != nil {
|
||||
wrappedPauseErr := fmt.Errorf("error pausing task %s, error: %s", name, pauseErr)
|
||||
log.Printf("[Scale] %s\n", wrappedPauseErr.Error())
|
||||
http.Error(w, wrappedPauseErr.Error(), http.StatusNotFound)
|
||||
return
|
||||
}
|
||||
}
|
||||
http.Error(w, "replicas must > 0 for faasd CE", http.StatusBadRequest)
|
||||
return
|
||||
}
|
||||
|
||||
if taskExists {
|
||||
if taskStatus != nil {
|
||||
if taskStatus.Status == containerd.Paused {
|
||||
if resumeErr := task.Resume(ctx); resumeErr != nil {
|
||||
log.Printf("[Scale] error resuming task %s, error: %s\n", name, resumeErr)
|
||||
http.Error(w, resumeErr.Error(), http.StatusBadRequest)
|
||||
if _, err := task.Delete(ctx); err != nil {
|
||||
log.Printf("[Scale] error deleting paused task %s, error: %s\n", name, err)
|
||||
http.Error(w, err.Error(), http.StatusBadRequest)
|
||||
return
|
||||
}
|
||||
} else if taskStatus.Status == containerd.Stopped {
|
||||
// Stopped tasks cannot be restarted, must be removed, and created again
|
||||
if _, delErr := task.Delete(ctx); delErr != nil {
|
||||
log.Printf("[Scale] error deleting stopped task %s, error: %s\n", name, delErr)
|
||||
http.Error(w, delErr.Error(), http.StatusBadRequest)
|
||||
if _, err := task.Delete(ctx); err != nil {
|
||||
log.Printf("[Scale] error deleting stopped task %s, error: %s\n", name, err)
|
||||
http.Error(w, err.Error(), http.StatusBadRequest)
|
||||
return
|
||||
}
|
||||
createNewTask = true
|
||||
|
Reference in New Issue
Block a user