diff --git a/.idea/codeStyles/Project.xml b/.idea/codeStyles/Project.xml
deleted file mode 100644
index ce889bd..0000000
--- a/.idea/codeStyles/Project.xml
+++ /dev/null
@@ -1,119 +0,0 @@
-
-
-
-
-
-
-
-
-
-
-
-
- xmlns:android
-
- ^$
-
-
-
-
-
-
-
-
- xmlns:.*
-
- ^$
-
-
- BY_NAME
-
-
-
-
-
-
- .*:id
-
- http://schemas.android.com/apk/res/android
-
-
-
-
-
-
-
-
- .*:name
-
- http://schemas.android.com/apk/res/android
-
-
-
-
-
-
-
-
- name
-
- ^$
-
-
-
-
-
-
-
-
- style
-
- ^$
-
-
-
-
-
-
-
-
- .*
-
- ^$
-
-
- BY_NAME
-
-
-
-
-
-
- .*
-
- http://schemas.android.com/apk/res/android
-
-
- ANDROID_ATTRIBUTE_ORDER
-
-
-
-
-
-
- .*
-
- .*
-
-
- BY_NAME
-
-
-
-
-
-
-
-
-
-
\ No newline at end of file
diff --git a/.idea/codeStyles/codeStyleConfig.xml b/.idea/codeStyles/codeStyleConfig.xml
deleted file mode 100644
index 79ee123..0000000
--- a/.idea/codeStyles/codeStyleConfig.xml
+++ /dev/null
@@ -1,5 +0,0 @@
-
-
-
-
-
\ No newline at end of file
diff --git a/.idea/compiler.xml b/.idea/compiler.xml
deleted file mode 100644
index b73660a..0000000
--- a/.idea/compiler.xml
+++ /dev/null
@@ -1,6 +0,0 @@
-
-
-
-
-
-
\ No newline at end of file
diff --git a/.idea/encodings.xml b/.idea/encodings.xml
deleted file mode 100644
index 15a15b2..0000000
--- a/.idea/encodings.xml
+++ /dev/null
@@ -1,4 +0,0 @@
-
-
-
-
\ No newline at end of file
diff --git a/.idea/inspectionProfiles/Project_Default.xml b/.idea/inspectionProfiles/Project_Default.xml
deleted file mode 100644
index 146ab09..0000000
--- a/.idea/inspectionProfiles/Project_Default.xml
+++ /dev/null
@@ -1,10 +0,0 @@
-
-
-
-
-
-
-
-
-
-
\ No newline at end of file
diff --git a/.idea/jarRepositories.xml b/.idea/jarRepositories.xml
deleted file mode 100644
index a5f05cd..0000000
--- a/.idea/jarRepositories.xml
+++ /dev/null
@@ -1,25 +0,0 @@
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
\ No newline at end of file
diff --git a/.idea/misc.xml b/.idea/misc.xml
deleted file mode 100644
index 355212c..0000000
--- a/.idea/misc.xml
+++ /dev/null
@@ -1,14 +0,0 @@
-
-
-
-
-
-
-
-
-
-
-
-
-
-
\ No newline at end of file
diff --git a/.idea/modules.xml b/.idea/modules.xml
deleted file mode 100644
index 50a28b1..0000000
--- a/.idea/modules.xml
+++ /dev/null
@@ -1,10 +0,0 @@
-
-
-
-
-
-
-
-
-
-
\ No newline at end of file
diff --git a/.idea/runConfigurations.xml b/.idea/runConfigurations.xml
deleted file mode 100644
index 7f68460..0000000
--- a/.idea/runConfigurations.xml
+++ /dev/null
@@ -1,12 +0,0 @@
-
-
-
-
-
-
\ No newline at end of file
diff --git a/.idea/vcs.xml b/.idea/vcs.xml
deleted file mode 100644
index 35eb1dd..0000000
--- a/.idea/vcs.xml
+++ /dev/null
@@ -1,6 +0,0 @@
-
-
-
-
-
-
\ No newline at end of file
diff --git a/gradle/wrapper/gradle-wrapper.properties b/gradle/wrapper/gradle-wrapper.properties
index 25d3265..3cd8500 100644
--- a/gradle/wrapper/gradle-wrapper.properties
+++ b/gradle/wrapper/gradle-wrapper.properties
@@ -1,5 +1,5 @@
distributionBase=GRADLE_USER_HOME
distributionPath=wrapper/dists
-distributionUrl=https\://services.gradle.org/distributions/gradle-6.8.2-all.zip
+distributionUrl=https\://services.gradle.org/distributions/gradle-7.3.1-all.zip
zipStoreBase=GRADLE_USER_HOME
zipStorePath=wrapper/dists
diff --git a/lib/src/main/java/com/kirkbushman/zammad/ZammadApi.kt b/lib/src/main/java/com/kirkbushman/zammad/ZammadApi.kt
index 983f3e8..9154ce1 100644
--- a/lib/src/main/java/com/kirkbushman/zammad/ZammadApi.kt
+++ b/lib/src/main/java/com/kirkbushman/zammad/ZammadApi.kt
@@ -28,6 +28,12 @@ interface ZammadApi {
@HeaderMap header: HashMap
): Call
+ @GET("/api/v1/signatures")
+ fun signatures(
+ @Query("expand") expanded: Boolean,
+ @HeaderMap header: HashMap
+ ): Call>
+
@FormUrlEncoded
@PUT("/api/v1/users/{id}")
fun updateUser(
@@ -213,6 +219,23 @@ interface ZammadApi {
@HeaderMap header: HashMap
): Call>
+ @GET("/api/v1/tags")
+ fun ticketTags(
+ @Query("object") ticket: String,
+ @Query("o_id") query: String,
+ @Query("expand") expanded: Boolean,
+ @HeaderMap header: HashMap
+ ): Call
+
+ @FormUrlEncoded
+ @POST("/api/v1/tags/add")
+ fun addTag(
+ @Field("item") item: String,
+ @Field("object") tagObject: String,
+ @Field("o_id") oId: String,
+ @HeaderMap header: HashMap
+ ): Call
+
@GET("/api/v1/ticket_states")
fun ticketStates(
@Query("expand") expanded: Boolean,
@@ -338,6 +361,7 @@ interface ZammadApi {
@Field("customer_id") customerId: Int? = null,
@Field("customer") customer: String? = null,
@Field("note") note: String? = null,
+ @Field("pending_time") pendingTime: String? = null,
@HeaderMap header: HashMap
): Call
diff --git a/lib/src/main/java/com/kirkbushman/zammad/ZammadClient.kt b/lib/src/main/java/com/kirkbushman/zammad/ZammadClient.kt
index 112ce26..8cf7b09 100644
--- a/lib/src/main/java/com/kirkbushman/zammad/ZammadClient.kt
+++ b/lib/src/main/java/com/kirkbushman/zammad/ZammadClient.kt
@@ -16,7 +16,7 @@ class ZammadClient(
private val logging: Boolean
) {
- constructor(baseUrl: String, username: String, password: String, logging: Boolean) : this(baseUrl, "$username:$password", logging)
+ constructor(baseUrl: String, username: String, password: String, logging: Boolean ) : this(baseUrl, "$username:$password", logging)
companion object {
@@ -52,11 +52,9 @@ class ZammadClient(
@Synchronized
fun getApi(baseUrl: String, logging: Boolean): ZammadApi {
synchronized(this) {
-
if (api == null) {
api = getRetrofit(baseUrl, logging).create(ZammadApi::class.java)
}
-
return api!!
}
}
@@ -85,13 +83,13 @@ class ZammadClient(
val api = getApi(baseUrl, logging)
val req = api.me(expanded, authMap)
val res = req.execute()
-
if (!res.isSuccessful) {
return null
}
return res.body()
}
+
}
private val api = getApi(baseUrl, logging)
@@ -632,6 +630,24 @@ class ZammadClient(
return res.body()
}
+ fun signatures(expanded: Boolean = false): List? {
+
+ val authMap = getHeaderMap()
+ val req = api.signatures(expanded, authMap)
+ val res = req.execute()
+
+ if (!res.isSuccessful) {
+
+ if (logging) {
+ Log.i("Retrofit Error", res.errorBody().toString())
+ }
+
+ return null
+ }
+
+ return res.body()
+ }
+
fun ticketStates(expanded: Boolean = false): List? {
val authMap = getHeaderMap()
@@ -979,7 +995,8 @@ class ZammadClient(
owner: String? = null,
customerId: Int? = null,
customer: String? = null,
- note: String? = null
+ note: String? = null,
+ pendingTime: String? = null
): Ticket? {
val authMap = getHeaderMap()
@@ -997,7 +1014,8 @@ class ZammadClient(
customerId = customerId,
customer = customer,
note = note,
- header = authMap
+ header = authMap,
+ pendingTime = pendingTime
)
val res = req.execute()
@@ -1037,6 +1055,42 @@ class ZammadClient(
return true
}
+ fun ticketTags(ticket: String, query: String, expanded: Boolean = false): TicketTags? {
+
+ val authMap = getHeaderMap()
+ val req = api.ticketTags(ticket, query, expanded, authMap)
+ val res = req.execute()
+
+ if (!res.isSuccessful) {
+
+ if (logging) {
+ Log.i("Retrofit Error", res.errorBody().toString())
+ }
+
+ return null
+ }
+
+ return res.body()
+ }
+
+ fun addTag(item: String, tagObject: String, oId: String): Any? {
+
+ val authMap = getHeaderMap()
+ val req = api.addTag(item, tagObject, oId, authMap)
+ val res = req.execute()
+
+ if (!res.isSuccessful) {
+
+ if (logging) {
+ Log.i("Retrofit Error", res.errorBody().toString())
+ }
+
+ return null
+ }
+
+ return res.body()
+ }
+
fun searchTickets(query: String, page: Int, perPage: Int, expanded: Boolean = false): SearchResult? {
val authMap = getHeaderMap()
diff --git a/lib/src/main/java/com/kirkbushman/zammad/models/MailSignature.kt b/lib/src/main/java/com/kirkbushman/zammad/models/MailSignature.kt
new file mode 100644
index 0000000..f0db002
--- /dev/null
+++ b/lib/src/main/java/com/kirkbushman/zammad/models/MailSignature.kt
@@ -0,0 +1,40 @@
+package com.kirkbushman.zammad.models
+
+import android.os.Parcelable
+import com.squareup.moshi.Json
+import com.squareup.moshi.JsonClass
+import kotlinx.parcelize.Parcelize
+
+@JsonClass(generateAdapter = true)
+@Parcelize
+data class MailSignature(
+
+ @Json(name = "id")
+ val id: Int,
+
+ @Json(name = "name")
+ val name: String,
+
+ @Json(name = "body")
+ val body: String,
+
+ @Json(name = "active")
+ val active: Boolean,
+
+ @Json(name = "note")
+ val note: String?,
+
+ @Json(name = "created_by_id")
+ val createdById: Int,
+
+ @Json(name = "updated_by_id")
+ val updatedById: Int,
+
+ @Json(name = "created_at")
+ val createdAt: String,
+
+ @Json(name = "updated_at")
+ val updatedAt: String,
+
+) : Parcelable
+
diff --git a/lib/src/main/java/com/kirkbushman/zammad/models/Ticket.kt b/lib/src/main/java/com/kirkbushman/zammad/models/Ticket.kt
index 93be453..20c8757 100644
--- a/lib/src/main/java/com/kirkbushman/zammad/models/Ticket.kt
+++ b/lib/src/main/java/com/kirkbushman/zammad/models/Ticket.kt
@@ -82,6 +82,9 @@ data class Ticket(
override val createdBy: String?,
@Json(name = "updated_by")
- override val updatedBy: String?
+ override val updatedBy: String?,
+
+ @Json(name = "pending_time")
+ val pendingTime: String?
) : Parcelable, Identifiable, Creatable, Updatable
diff --git a/lib/src/main/java/com/kirkbushman/zammad/models/TicketState.kt b/lib/src/main/java/com/kirkbushman/zammad/models/TicketState.kt
index 78e2969..2fdfe2d 100644
--- a/lib/src/main/java/com/kirkbushman/zammad/models/TicketState.kt
+++ b/lib/src/main/java/com/kirkbushman/zammad/models/TicketState.kt
@@ -31,7 +31,7 @@ data class TicketState(
val defaultFollowUp: Boolean,
@Json(name = "note")
- val note: String,
+ val note: String?,
@Json(name = "created_by_id")
override val createdById: Int,
diff --git a/lib/src/main/java/com/kirkbushman/zammad/models/TicketTags.kt b/lib/src/main/java/com/kirkbushman/zammad/models/TicketTags.kt
new file mode 100644
index 0000000..02dfd56
--- /dev/null
+++ b/lib/src/main/java/com/kirkbushman/zammad/models/TicketTags.kt
@@ -0,0 +1,16 @@
+package com.kirkbushman.zammad.models
+
+import android.os.Parcelable
+import com.squareup.moshi.Json
+import com.squareup.moshi.JsonClass
+import kotlinx.parcelize.Parcelize
+import kotlinx.parcelize.RawValue
+
+@JsonClass(generateAdapter = true)
+@Parcelize
+data class TicketTags(
+
+ @Json(name = "tags")
+ val tags: @RawValue List
+
+) : Parcelable
\ No newline at end of file
diff --git a/lib/src/main/java/com/kirkbushman/zammad/models/compat/TicketCompat.kt b/lib/src/main/java/com/kirkbushman/zammad/models/compat/TicketCompat.kt
index 65d4197..ffe7fde 100644
--- a/lib/src/main/java/com/kirkbushman/zammad/models/compat/TicketCompat.kt
+++ b/lib/src/main/java/com/kirkbushman/zammad/models/compat/TicketCompat.kt
@@ -46,6 +46,9 @@ data class TicketCompat(
val article: TicketArticleCompat,
@Json(name = "note")
- val note: String? = null
+ val note: String? = null,
+
+ @Json(name = "pending_time")
+ val pendingTime: String? = null
) : Parcelable
diff --git a/sampleapp/src/main/AndroidManifest.xml b/sampleapp/src/main/AndroidManifest.xml
index 862da94..169181d 100644
--- a/sampleapp/src/main/AndroidManifest.xml
+++ b/sampleapp/src/main/AndroidManifest.xml
@@ -20,7 +20,9 @@
tools:targetApi="n"
tools:ignore="GoogleAppIndexingWarning">
-
+
@@ -28,45 +30,45 @@
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
-
\ No newline at end of file
+
diff --git a/sampleapp/src/main/java/com/kirkbushman/sampleapp/LoginActivity.kt b/sampleapp/src/main/java/com/kirkbushman/sampleapp/LoginActivity.kt
index 5819625..d09ad11 100644
--- a/sampleapp/src/main/java/com/kirkbushman/sampleapp/LoginActivity.kt
+++ b/sampleapp/src/main/java/com/kirkbushman/sampleapp/LoginActivity.kt
@@ -2,14 +2,16 @@ package com.kirkbushman.sampleapp
import android.content.Intent
import android.os.Bundle
+import android.util.Base64
import android.widget.Toast
import androidx.appcompat.app.AppCompatActivity
import com.kirkbushman.sampleapp.data.Preferences
import com.kirkbushman.sampleapp.databinding.ActivityLoginBinding
import com.kirkbushman.sampleapp.di.SingletonModule
import com.kirkbushman.zammad.ZammadClient
-import com.kirkbushman.zammad.models.User
import dagger.hilt.android.AndroidEntryPoint
+import java.net.HttpURLConnection
+import java.net.URL
import javax.inject.Inject
@AndroidEntryPoint
@@ -28,7 +30,7 @@ class LoginActivity : AppCompatActivity() {
if (prefs.getIsLoggedIn()) {
- SingletonModule.setClient(ZammadClient(prefs.getBaseUrl(), prefs.getUsername(), prefs.getPassword(), true))
+ SingletonModule.setClient(ZammadClient(prefs.getBaseUrl(), prefs.getUsername(), prefs.getPassword(), true ))
startActivity(Intent(this, MainActivity::class.java))
}
@@ -39,7 +41,7 @@ class LoginActivity : AppCompatActivity() {
val username = binding.emailEdit.text.trim().toString()
val password = binding.passwordEdit.text.trim().toString()
- if (baseUrl == "") {
+ if (!baseUrl.contains("https://")) {
Toast.makeText(this, "baseurl not found!", Toast.LENGTH_SHORT).show()
}
@@ -51,30 +53,69 @@ class LoginActivity : AppCompatActivity() {
Toast.makeText(this, "password not found!", Toast.LENGTH_SHORT).show()
}
- var me: User? = null
- DoAsync(
- doWork = {
- me = ZammadClient.me(baseUrl, username, password, true)
- },
- onPost = {
-
- if (me != null) {
-
- SingletonModule.setClient(ZammadClient(baseUrl, username, password, true))
-
- with(prefs) {
- setIsLoggedIn(true)
- setBaseUrl(baseUrl)
- setUsername(username)
- setPassword(password)
+ else {
+ var logText: String?
+ var isReachable:Int?=null
+ DoAsync(
+ doWork = {
+ kotlin.runCatching {
+ val userpass = "$username:$password"
+ val basicAuth = "Basic " + Base64.encodeToString(
+ userpass.toByteArray(),
+ Base64.NO_WRAP
+ )
+
+ isReachable =
+ if (android.os.Build.VERSION.SDK_INT >= 25) {
+ val connection: HttpURLConnection = URL(
+ baseUrl + "/api/v1/users/me"
+ ).openConnection() as HttpURLConnection
+ connection.setRequestProperty("Authorization", basicAuth);
+ connection.requestMethod = "GET"
+ connection.responseCode
+ } else 200
+ }
+ },
+ onPost = {
+ if (isReachable != 200) {
+ Toast.makeText(
+ this,
+ getString(R.string.inaccessible_error) + "\nERROR: " + isReachable.toString(),
+ Toast.LENGTH_LONG
+ )
+ .show()
+ return@DoAsync
+ }
+ logText = if (isReachable == 401) getString(R.string.unauthorized_error) else getString(
+ R.string.inaccessible_error
+ )
+
+ if (isReachable == 200) {
+
+ SingletonModule.setClient(
+ ZammadClient(
+ baseUrl,
+ username,
+ password,
+ true
+ )
+ )
+
+ with(prefs) {
+ setIsLoggedIn(true)
+ setBaseUrl(baseUrl)
+ setUsername(username)
+ setPassword(password)
+ }
+
+ startActivity(Intent(this, MainActivity::class.java))
+ } else {
+ Toast.makeText(this, logText, Toast.LENGTH_LONG)
+ .show()
}
-
- startActivity(Intent(this, MainActivity::class.java))
- } else {
- Toast.makeText(this, "Error while trying to login!", Toast.LENGTH_SHORT).show()
}
- }
- )
+ )
+ }
}
}
}
diff --git a/sampleapp/src/main/res/values/strings.xml b/sampleapp/src/main/res/values/strings.xml
index 68f774c..b7a2bca 100644
--- a/sampleapp/src/main/res/values/strings.xml
+++ b/sampleapp/src/main/res/values/strings.xml
@@ -55,4 +55,6 @@
Search:
No items to show.
+ Error while trying to login!\nUnauthorized! Please check your username and password.
+ Error while trying to login!\nUrl is inaccessible! Check network and input!