Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
25 commits
Select commit Hold shift + click to select a range
4ae3f53
feat: Implement chat auto-reply feature
google-labs-jules[bot] May 26, 2025
83015fc
Merge pull request #1 from rakshabesafe/feat/chat-autoreply
rakshabesafe May 26, 2025
2994d3a
Update main.go
rakshabesafe May 26, 2025
fa0a96c
Update Dockerfile
rakshabesafe May 26, 2025
291892c
feat: Implement WhatsApp autoreply feature
google-labs-jules[bot] May 26, 2025
4935c8a
Merge pull request #2 from rakshabesafe/feature/autoreply
rakshabesafe May 26, 2025
ab23e53
Update main.go
rakshabesafe May 26, 2025
b945ed9
Update wmiau.go
rakshabesafe May 26, 2025
7c6f1de
Create adduser.sh
rakshabesafe May 26, 2025
a396f37
feat: Implement autoreply modes functionality
google-labs-jules[bot] May 26, 2025
f0d20e0
feat: Implement autoreply modes and Google Contacts integration
google-labs-jules[bot] Jun 1, 2025
0fcf450
fix: Add missing strings import to db.go
google-labs-jules[bot] Jun 5, 2025
524269b
feat: Implement live Google Contacts fetching for autoreply modes
google-labs-jules[bot] Jun 5, 2025
226c815
refactor: Standardize autoreply URLs and Swagger tags
google-labs-jules[bot] Jun 5, 2025
b07092d
fix: Add missing io import to handlers.go
google-labs-jules[bot] Jun 5, 2025
b1a9405
fix: Correct database table creation order
google-labs-jules[bot] Jun 5, 2025
9b01d1e
refactor: Remove unused strings import from db.go
google-labs-jules[bot] Jun 5, 2025
8ce1e48
I've addressed an issue in the migrations.go file. It was using `log.…
google-labs-jules[bot] Jun 5, 2025
4b404b3
fix: Remove duplicate AutoReplyEntry definition in spec.yml
google-labs-jules[bot] Jun 5, 2025
a56416a
refactor: Isolate Google Contacts logic into separate files
google-labs-jules[bot] Jun 5, 2025
315b617
fix: Correct syntax errors in handlers
google-labs-jules[bot] Jun 5, 2025
a63eaef
fix: Resolve redeclaration and usage errors
google-labs-jules[bot] Jun 5, 2025
a8cb87a
Jules was unable to complete the task in time. Please review the work…
google-labs-jules[bot] Jun 6, 2025
ea9e125
refactor: Consolidate all handlers into handlers.go for upstream alig…
google-labs-jules[bot] Jun 7, 2025
cf13b53
fix: Replace respondWithJSON with Respond in admin handlers
google-labs-jules[bot] Jun 8, 2025
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
58 changes: 58 additions & 0 deletions API.md
Original file line number Diff line number Diff line change
Expand Up @@ -705,6 +705,64 @@ curl -s -X POST -H 'Token: 1234ABCD' -H 'Content-Type: application/json' --data

---

### Add/Update Auto-Reply
* **Method:** `POST`
* **Path:** `/chat/autoreply`
* **Description:** Sets up an auto-reply for a specific phone number. If an auto-reply for the given phone number already exists for the user, it will be updated. If not, a new one will be created.
* **Authentication:** Requires user token.
* **Request Body (JSON):**
```json
{
"Phone": "1234567890", // Target phone number (normalized, e.g., digits only or international format used by the system)
"Body": "Hello! I am currently unavailable and will get back to you soon."
}
```
* **Responses:**
* `201 Created`: If a new auto-reply was successfully created.
```json
{
"code": 201,
"data": {
"detail": "Auto-reply added successfully",
"id": "generated-unique-id-for-the-rule"
},
"success": true
}
```
* `400 Bad Request`: If `Phone` or `Body` is missing or invalid.
* `409 Conflict`: If an auto-reply for this phone number already exists for the user.
Comment on lines +711 to +733
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

high

The description for Add/Update Auto-Reply (line 711) states, "If an auto-reply for the given phone number already exists for the user, it will be updated." However, the 409 Conflict response (line 733) is documented for the case "If an auto-reply for this phone number already exists for the user."

This seems contradictory. The current handler implementation (handlers.go:AddAutoReply) also reflects an "add-only" behavior, returning a 409 Conflict if the entry exists, rather than updating it.

Could you clarify the intended behavior?

  • If it's "add-only", the description on line 711 should be updated to reflect this, and the 409 Conflict is appropriate.
  • If it's meant to be an "add-or-update" (upsert) operation, the handler logic in handlers.go would need to be changed (e.g., using ON CONFLICT DO UPDATE for PostgreSQL and INSERT OR REPLACE or equivalent for SQLite), and the success status code might need adjustment (e.g., 200 OK for update, 201 Created for new).

* `500 Internal Server Error`: For other server-side errors.

---

### Delete Auto-Reply
* **Method:** `DELETE`
* **Path:** `/chat/autoreply`
* **Description:** Deletes an existing auto-reply for a specific phone number for the authenticated user.
* **Authentication:** Requires user token.
* **Request Body (JSON):**
```json
{
"Phone": "1234567890" // Target phone number whose auto-reply rule should be deleted.
}
```
* **Responses:**
* `200 OK`: If the auto-reply was successfully deleted.
```json
{
"code": 200,
"data": {
"detail": "Auto-reply deleted successfully"
},
"success": true
}
```
* `400 Bad Request`: If `Phone` is missing or invalid.
* `404 Not Found`: If no auto-reply rule exists for the given phone number for this user.
* `500 Internal Server Error`: For other server-side errors.

---

## Download Document

Downloads a Document from a message and retrieves it Base64 media encoded. Required request parameters are: Url, MediaKey, Mimetype, FileSHA256 and FileLength
Expand Down
4 changes: 2 additions & 2 deletions Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ RUN apk update && apk add --no-cache \
ffmpeg \
tzdata

ENV TZ="America/Sao_Paulo"
ENV TZ="Asia/Kolkata"
WORKDIR /app

COPY --from=builder /app/wuzapi /app/
Expand All @@ -34,4 +34,4 @@ RUN chown -R root:root /app

VOLUME [ "/app/dbdata", "/app/files" ]

ENTRYPOINT ["/app/wuzapi", "--logtype=console", "--color=true"]
ENTRYPOINT ["/app/wuzapi", "--logtype=console", "--color=true"]
22 changes: 22 additions & 0 deletions adduser.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
#!/bin/bash

# Script to create a user via curl

# Validate the number of arguments
if [ "$#" -ne 3 ]; then
echo "Usage: $0 <adminpass> <username> <passwd>"
exit 1
fi

# Assign arguments to variables
ADMIN_PASS="$1"
USERNAME="$2"
USER_PASSWD="$3"

# Execute the curl command
curl -X POST http://localhost:8089/admin/users \
-H "Authorization: ${ADMIN_PASS}" \
-H "Content-Type: application/json" \
-d "{\"name\": \"${USERNAME}\", \"token\": \"${USER_PASSWD}\"}"

echo # Add a newline for cleaner output
28 changes: 28 additions & 0 deletions autoreply_routes.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
package main

import (
"github.com/gorilla/mux"
"github.com/justinas/alice"
)

func registerAutoreplyRoutes(s *server, r *mux.Router, c alice.Chain) {
// Simple Autoreply routes (formerly in /chat/autoreply)
r.Handle("/chat/autoreply", c.Then(s.AddAutoReply())).Methods("POST")
r.Handle("/chat/autoreply", c.Then(s.DeleteAutoReply())).Methods("DELETE")
r.Handle("/chat/autoreply", c.Then(s.GetAutoReplies())).Methods("GET")

// Mode Autoreply routes (formerly /mode/..., now /autoreply/...)
r.Handle("/autoreply/mode", c.Then(s.AddModeAutoreply())).Methods("POST")
r.Handle("/autoreply/mode", c.Then(s.GetModeAutoreplies())).Methods("GET")
r.Handle("/autoreply/mode", c.Then(s.DeleteModeAutoreply())).Methods("DELETE")

r.Handle("/autoreply/enablemode", c.Then(s.EnableMode())).Methods("POST")
r.Handle("/autoreply/disablemode", c.Then(s.DisableMode())).Methods("POST")
r.Handle("/autoreply/currentmode", c.Then(s.GetCurrentMode())).Methods("GET")
r.Handle("/autoreply/clearmode", c.Then(s.ClearModes())).Methods("POST")

// Google Contacts integration routes (already under /autoreply/)
r.Handle("/autoreply/contactgroupauth", c.Then(s.SetGoogleContactsAuthToken())).Methods("POST")
r.Handle("/autoreply/contactgroup", c.Then(s.AddContactGroupToMode())).Methods("POST")
r.Handle("/autoreply/contactgroup", c.Then(s.DeleteContactGroupFromMode())).Methods("DELETE")
}
4 changes: 4 additions & 0 deletions constants.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
package main

// supportedEventTypes lists the valid event types for webhooks.
var supportedEventTypes = []string{"Message", "ReadReceipt", "Presence", "HistorySync", "ChatPresence", "All"}
39 changes: 35 additions & 4 deletions db.go
Original file line number Diff line number Diff line change
Expand Up @@ -24,9 +24,42 @@ func InitializeDatabase(exPath string) (*sqlx.DB, error) {
config := getDatabaseConfig(exPath)

if config.Type == "postgres" {
return initializePostgres(config)
db, err := initializePostgres(config)
if err != nil {
return nil, err
}
// Create tables for postgres
if err := createTables(db, "postgres"); err != nil {
return nil, fmt.Errorf("failed to create tables for postgres: %w", err)
}
return db, nil
}

// Default to SQLite
db, err := initializeSQLite(config)
if err != nil {
return nil, err
}
// Call to createTables can be removed if it becomes entirely empty,
// or left if it might handle other non-migrated setup in the future.
// For now, it will be called but do nothing.
if err := createTables(db, "sqlite"); err != nil {
return nil, fmt.Errorf("failed to create tables for sqlite: %w", err)
}
return initializeSQLite(config)
return db, nil
}

func createTables(db *sqlx.DB, dbType string) error {
// The logic for creating autoreply_modes and active_mode tables
// has been moved to the migration system.
// See migrations with ID 6 and 7.

// The logic for adding google_contacts_auth_token has also been moved to migrations (ID 5).

// This function is currently a no-op but is kept in case there are future needs
// for table setup outside the main migration sequence or for other DB types
// not covered by the current migration logic.
return nil
}

func getDatabaseConfig(exPath string) DatabaseConfig {
Expand Down Expand Up @@ -70,7 +103,6 @@ func initializePostgres(config DatabaseConfig) (*sqlx.DB, error) {
if err := db.Ping(); err != nil {
return nil, fmt.Errorf("failed to ping postgres database: %w", err)
}

return db, nil
}

Expand All @@ -89,6 +121,5 @@ func initializeSQLite(config DatabaseConfig) (*sqlx.DB, error) {
if err := db.Ping(); err != nil {
return nil, fmt.Errorf("failed to ping sqlite database: %w", err)
}

return db, nil
}
Loading