[Git][java-team/libpostgresql-jdbc-java][master] 3 commits: New upstream version 42.3.5
Christoph Berg (@myon)
gitlab at salsa.debian.org
Fri May 6 15:51:42 BST 2022
Christoph Berg pushed to branch master at Debian Java Maintainers / libpostgresql-jdbc-java
Commits:
4e9f0e47 by Christoph Berg at 2022-05-06T16:50:56+02:00
New upstream version 42.3.5
- - - - -
eb80f3c9 by Christoph Berg at 2022-05-06T16:50:59+02:00
Update upstream source from tag 'upstream/42.3.5'
Update to upstream version '42.3.5'
with Debian dir feaaa0ce1ea9a501b99449d5d56144bf17455af4
- - - - -
7ee8e795 by Christoph Berg at 2022-05-06T16:51:30+02:00
New upstream version 42.3.5.
- - - - -
13 changed files:
- README.md
- debian/changelog
- pom.xml
- src/main/java/org/postgresql/PGProperty.java
- src/main/java/org/postgresql/core/PGStream.java
- src/main/java/org/postgresql/hostchooser/HostRequirement.java
- src/main/java/org/postgresql/hostchooser/MultiHostChooser.java
- src/main/java/org/postgresql/jdbc/PgResultSet.java
- src/main/java/org/postgresql/jdbc/TimestampUtils.java
- src/main/java/org/postgresql/util/DriverInfo.java
- src/main/resources/META-INF/MANIFEST.MF
- src/test/java/org/postgresql/test/hostchooser/MultiHostsConnectionTest.java
- src/test/java/org/postgresql/test/jdbc42/TimestampUtilsTest.java
Changes:
=====================================
README.md
=====================================
@@ -122,13 +122,13 @@ In addition to the standard connection parameters the driver supports a number o
| connectTimeout | Integer | 10 | The timeout value used for socket connect operations. |
| socketTimeout | Integer | 0 | The timeout value used for socket read operations. |
| tcpKeepAlive | Boolean | false | Enable or disable TCP keep-alive. |
-| tcpNoDelay | Boolean | false | Enable or disable TCP no delay. |
+| tcpNoDelay | Boolean | true | Enable or disable TCP no delay. |
| ApplicationName | String | PostgreSQL JDBC Driver | The application name (require server version >= 9.0). If assumeMinServerVersion is set to >= 9.0 this will be sent in the startup packets, otherwise after the connection is made |
| readOnly | Boolean | false | Puts this connection in read-only mode |
| disableColumnSanitiser | Boolean | false | Enable optimization that disables column name sanitiser |
| assumeMinServerVersion | String | null | Assume the server is at least that version |
| currentSchema | String | null | Specify the schema (or several schema separated by commas) to be set in the search-path |
-| targetServerType | String | any | Specifies what kind of server to connect, possible values: any, master, slave (deprecated), secondary, preferSlave (deprecated), preferSecondary |
+| targetServerType | String | any | Specifies what kind of server to connect, possible values: any, master, slave (deprecated), secondary, preferSlave (deprecated), preferSecondary, preferPrimary |
| hostRecheckSeconds | Integer | 10 | Specifies period (seconds) after which the host status is checked again in case it has changed |
| loadBalanceHosts | Boolean | false | If disabled hosts are connected in the given order. If enabled hosts are chosen randomly from the set of suitable candidates |
| socketFactory | String | null | Specify a socket factory for socket creation |
=====================================
debian/changelog
=====================================
@@ -1,3 +1,9 @@
+libpgjava (42.3.5-1) unstable; urgency=medium
+
+ * New upstream version 42.3.5.
+
+ -- Christoph Berg <myon at debian.org> Fri, 06 May 2022 16:51:03 +0200
+
libpgjava (42.3.4-1) unstable; urgency=medium
* New upstream version 42.3.4.
=====================================
pom.xml
=====================================
@@ -10,7 +10,7 @@
<artifactId>postgresql</artifactId>
<packaging>jar</packaging>
<name>PostgreSQL JDBC Driver - JDBC 4.2</name>
- <version>42.3.4</version>
+ <version>42.3.5</version>
<description>Java JDBC 4.2 (JRE 8+) driver for PostgreSQL database</description>
<url>https://github.com/pgjdbc/pgjdbc</url>
=====================================
src/main/java/org/postgresql/PGProperty.java
=====================================
@@ -693,7 +693,7 @@ public enum PGProperty {
"any",
"Specifies what kind of server to connect",
false,
- new String [] {"any", "primary", "master", "slave", "secondary", "preferSlave", "preferSecondary"}),
+ new String [] {"any", "primary", "master", "slave", "secondary", "preferSlave", "preferSecondary", "preferPrimary"}),
/**
* Enable or disable TCP keep-alive. The default is {@code false}.
@@ -705,8 +705,8 @@ public enum PGProperty {
TCP_NO_DELAY(
"tcpNoDelay",
- "false",
- "Enable or disable TCP no delay. The default is (@code false}."
+ "true",
+ "Enable or disable TCP no delay. The default is (@code true}."
),
/**
* Specifies the length to return for types of unknown length.
=====================================
src/main/java/org/postgresql/core/PGStream.java
=====================================
@@ -113,7 +113,7 @@ public class PGStream implements Closeable, Flushable {
int receiveBufferSize = 1024;
int soTimeout = 0;
boolean keepAlive = false;
- boolean tcpNoDelay = false;
+ boolean tcpNoDelay = true;
/*
Get the existing values before closing the stream
=====================================
src/main/java/org/postgresql/hostchooser/HostRequirement.java
=====================================
@@ -40,6 +40,11 @@ public enum HostRequirement {
public boolean allowConnectingTo(/* @Nullable */ HostStatus status) {
return status != HostStatus.ConnectFail;
}
+ },
+ preferPrimary {
+ public boolean allowConnectingTo(/* @Nullable */ HostStatus status) {
+ return status != HostStatus.ConnectFail;
+ }
};
public abstract boolean allowConnectingTo(/* @Nullable */ HostStatus status);
=====================================
src/main/java/org/postgresql/hostchooser/MultiHostChooser.java
=====================================
@@ -14,7 +14,6 @@ import org.postgresql.util.PSQLException;
import java.util.AbstractList;
import java.util.ArrayList;
import java.util.Arrays;
-import java.util.Collections;
import java.util.Iterator;
import java.util.List;
import java.util.Properties;
@@ -47,8 +46,8 @@ class MultiHostChooser implements HostChooser {
// In case all the candidate hosts are unavailable or do not match, try all the hosts just in case
List<HostSpec> allHosts = Arrays.asList(hostSpecs);
if (loadBalance) {
- allHosts = new ArrayList<HostSpec>(allHosts);
- Collections.shuffle(allHosts);
+ allHosts = new ArrayList<>(allHosts);
+ shuffle(allHosts);
}
res = withReqStatus(targetServerType, allHosts).iterator();
}
@@ -56,32 +55,33 @@ class MultiHostChooser implements HostChooser {
}
private Iterator<CandidateHost> candidateIterator() {
- if (targetServerType != HostRequirement.preferSecondary) {
+ if ( targetServerType != HostRequirement.preferSecondary
+ && targetServerType != HostRequirement.preferPrimary ) {
return getCandidateHosts(targetServerType).iterator();
}
+ HostRequirement preferredServerType =
+ targetServerType == HostRequirement.preferSecondary
+ ? HostRequirement.secondary
+ : HostRequirement.primary;
+
// preferSecondary tries to find secondary hosts first
// Note: sort does not work here since there are "unknown" hosts,
// and that "unknown" might turn out to be master, so we should discard that
// if other secondaries exist
- List<CandidateHost> secondaries = getCandidateHosts(HostRequirement.secondary);
+ // Same logic as the above works for preferPrimary if we replace "secondary"
+ // with "primary" and vice versa
+ List<CandidateHost> preferred = getCandidateHosts(preferredServerType);
List<CandidateHost> any = getCandidateHosts(HostRequirement.any);
- if (secondaries.isEmpty()) {
- return any.iterator();
- }
-
- if (any.isEmpty()) {
- return secondaries.iterator();
- }
-
- if (secondaries.get(secondaries.size() - 1).equals(any.get(0))) {
- // When the last secondary's hostspec is the same as the first in "any" list, there's no need
- // to attempt to connect it as "secondary"
+ if ( !preferred.isEmpty() && !any.isEmpty()
+ && preferred.get(preferred.size() - 1).hostSpec.equals(any.get(0).hostSpec)) {
+ // When the last preferred host's hostspec is the same as the first in "any" list, there's no need
+ // to attempt to connect it as "preferred"
// Note: this is only an optimization
- secondaries = rtrim(1, secondaries);
+ preferred = rtrim(1, preferred);
}
- return append(secondaries, any).iterator();
+ return append(preferred, any).iterator();
}
private List<CandidateHost> getCandidateHosts(HostRequirement hostRequirement) {
=====================================
src/main/java/org/postgresql/jdbc/PgResultSet.java
=====================================
@@ -74,6 +74,7 @@ import java.time.LocalDateTime;
import java.time.LocalTime;
import java.time.OffsetDateTime;
import java.time.OffsetTime;
+import java.time.ZoneOffset;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Calendar;
@@ -671,8 +672,19 @@ public class PgResultSet implements ResultSet, org.postgresql.PGRefCursorResultS
}
} else {
// string
- if (oid == Oid.TIMESTAMPTZ || oid == Oid.TIMESTAMP || oid == Oid.TIMETZ) {
- return getTimestampUtils().toOffsetDateTime(castNonNull(getString(i)), oid != Oid.TIMETZ);
+
+ if (oid == Oid.TIMESTAMPTZ || oid == Oid.TIMESTAMP ) {
+
+ OffsetDateTime offsetDateTime = getTimestampUtils().toOffsetDateTime(castNonNull(getString(i)));
+ if ( offsetDateTime != OffsetDateTime.MAX && offsetDateTime != OffsetDateTime.MIN ) {
+ return offsetDateTime.withOffsetSameInstant(ZoneOffset.UTC);
+ } else {
+ return offsetDateTime;
+ }
+
+ }
+ if ( oid == Oid.TIMETZ ) {
+ return getTimestampUtils().toOffsetDateTime(castNonNull(getString(i)));
}
}
=====================================
src/main/java/org/postgresql/jdbc/TimestampUtils.java
=====================================
@@ -516,17 +516,30 @@ public class TimestampUtils {
}
}
+ /**
+ * Returns the offset date time object matching the given bytes with Oid#TIMETZ.
+ * Not used internally anymore, function is here to retain compatibility with previous versions
+ *
+ * @param t the time value
+ * @return the matching offset date time
+ * @deprecated was used internally, and not used anymore
+ */
+ @Deprecated
+ public OffsetDateTime toOffsetDateTime(Time t) {
+ // hardcode utc because the backend does not provide us the timezone
+ // hardcode UNIX epoch, JDBC requires OffsetDateTime but doesn't describe what date should be used
+ return t.toLocalTime().atDate(LocalDate.of(1970, 1, 1)).atOffset(ZoneOffset.UTC);
+ }
+
/**
* Parse a string and return a OffsetDateTime representing its value.
*
- * @param s The ISO formated date string to parse.
- * @param adaptToUTC if true the timezone is adapted to be UTC;
- * this must be done for timestamp and timestamptz as they have no zone on server side
+ * @param s The ISO formatted date string to parse.
* @return null if s is null or a OffsetDateTime of the parsed string s.
* @throws SQLException if there is a problem parsing s.
*/
public /* @PolyNull */ OffsetDateTime toOffsetDateTime(
- /* @PolyNull */ String s, boolean adaptToUTC) throws SQLException {
+ /* @PolyNull */ String s) throws SQLException {
if (s == null) {
return null;
}
@@ -545,9 +558,6 @@ public class TimestampUtils {
final ParsedTimestamp ts = parseBackendTimestamp(s);
OffsetDateTime result =
OffsetDateTime.of(ts.year, ts.month, ts.day, ts.hour, ts.minute, ts.second, ts.nanos, ts.offset);
- if (adaptToUTC) {
- result = result.withOffsetSameInstant(ZoneOffset.UTC);
- }
if (ts.era == GregorianCalendar.BC) {
return result.with(ChronoField.ERA, IsoEra.BCE.getValue());
} else {
=====================================
src/main/java/org/postgresql/util/DriverInfo.java
=====================================
@@ -16,13 +16,13 @@ public final class DriverInfo {
// Driver name
public static final String DRIVER_NAME = "PostgreSQL JDBC Driver";
public static final String DRIVER_SHORT_NAME = "PgJDBC";
- public static final String DRIVER_VERSION = "42.3.4";
+ public static final String DRIVER_VERSION = "42.3.5";
public static final String DRIVER_FULL_NAME = DRIVER_NAME + " " + DRIVER_VERSION;
// Driver version
public static final int MAJOR_VERSION = 42;
public static final int MINOR_VERSION = 3;
- public static final int PATCH_VERSION = 4;
+ public static final int PATCH_VERSION = 5;
// JDBC specification
public static final String JDBC_VERSION = "4.2";
=====================================
src/main/resources/META-INF/MANIFEST.MF
=====================================
@@ -2,7 +2,7 @@ Manifest-Version: 1.0
Implementation-Title: PostgreSQL JDBC Driver
Bundle-License: BSD-2-Clause
Automatic-Module-Name: org.postgresql.jdbc
-Implementation-Version: 42.3.4
+Implementation-Version: 42.3.5
Specification-Vendor: Oracle Corporation
Specification-Title: JDBC
Implementation-Vendor-Id: org.postgresql
=====================================
src/test/java/org/postgresql/test/hostchooser/MultiHostsConnectionTest.java
=====================================
@@ -14,6 +14,7 @@ import static org.junit.Assert.assertTrue;
import static org.junit.Assert.fail;
import static org.junit.Assume.assumeTrue;
import static org.postgresql.hostchooser.HostRequirement.any;
+import static org.postgresql.hostchooser.HostRequirement.preferPrimary;
import static org.postgresql.hostchooser.HostRequirement.preferSecondary;
import static org.postgresql.hostchooser.HostRequirement.primary;
import static org.postgresql.hostchooser.HostRequirement.secondary;
@@ -237,6 +238,27 @@ public class MultiHostsConnectionTest {
assertGlobalState(secondary1, "Secondary"); // was unknown, so tried to connect in order
}
+ @Test
+ public void testConnectToPrimaryFirst() throws SQLException {
+ getConnection(preferPrimary, true, fake1, primary1, secondary1);
+ assertRemote(primaryIp);
+ assertGlobalState(fake1, "ConnectFail");
+ assertGlobalState(primary1, "Primary");
+ assertGlobalState(secondary1, null);
+
+ getConnection(primary, false, fake1, secondary1, primary1);
+ assertRemote(primaryIp);
+ assertGlobalState(fake1, "ConnectFail");
+ assertGlobalState(primary1, "Primary");
+ assertGlobalState(secondary1, "Secondary"); // tried as it was unknown
+
+ getConnection(preferPrimary, true, fake1, secondary1, primary1);
+ assertRemote(primaryIp);
+ assertGlobalState(fake1, "ConnectFail");
+ assertGlobalState(primary1, "Primary");
+ assertGlobalState(secondary1, "Secondary");
+ }
+
@Test
public void testConnectToPrimaryWithReadonlyTransactionMode() throws SQLException {
con = TestUtil.openPrivilegedDB();
@@ -322,6 +344,47 @@ public class MultiHostsConnectionTest {
assertTrue("Never tried to connect to fake node", fake1FoundTried);
}
+ @Test
+ public void testLoadBalancing_preferPrimary() throws SQLException {
+ Set<String> connectedHosts = new HashSet<String>();
+ Set<HostSpec> tryConnectedHosts = new HashSet<HostSpec>();
+ for (int i = 0; i < 20; ++i) {
+ getConnection(preferPrimary, true, true, fake1, secondary1, secondary2, primary1);
+ connectedHosts.add(getRemoteHostSpec());
+ tryConnectedHosts.addAll(hostStatusMap.keySet());
+ if (tryConnectedHosts.size() == 4) {
+ break;
+ }
+ }
+
+ assertRemote(primaryIp);
+ assertEquals("Connected to hosts other than primary", new HashSet<String>(asList(primaryIp)),
+ connectedHosts);
+ assertEquals("Never tried to connect to fake node", 4, tryConnectedHosts.size());
+
+ getConnection(preferPrimary, false, true, fake1, secondary1, primary1);
+ assertRemote(primaryIp);
+
+ // connect to secondaries when there's no primary - with load balancing
+ connectedHosts.clear();
+ for (int i = 0; i < 20; ++i) {
+ getConnection(preferPrimary, false, true, fake1, secondary1, secondary2);
+ connectedHosts.add(getRemoteHostSpec());
+ if (connectedHosts.size() == 2) {
+ break;
+ }
+ }
+ assertEquals("Never connected to all secondary hosts", new HashSet<String>(asList(secondaryIP, secondaryIP2)),
+ connectedHosts);
+
+ // connect to secondary when there's no primary
+ getConnection(preferPrimary, true, true, fake1, secondary1);
+ assertRemote(secondaryIP);
+
+ getConnection(preferPrimary, false, true, fake1, secondary1);
+ assertRemote(secondaryIP);
+ }
+
@Test
public void testLoadBalancing_preferSecondary() throws SQLException {
Set<String> connectedHosts = new HashSet<String>();
=====================================
src/test/java/org/postgresql/test/jdbc42/TimestampUtilsTest.java
=====================================
@@ -27,54 +27,66 @@ public class TimestampUtilsTest {
@Test
public void testToStringOfLocalTime() {
- assertToStringOfLocalTime("00:00:00", "00:00:00");
- assertToStringOfLocalTime("00:00:00.1", "00:00:00.1");
- assertToStringOfLocalTime("00:00:00.12", "00:00:00.12");
- assertToStringOfLocalTime("00:00:00.123", "00:00:00.123");
- assertToStringOfLocalTime("00:00:00.1234", "00:00:00.1234");
- assertToStringOfLocalTime("00:00:00.12345", "00:00:00.12345");
- assertToStringOfLocalTime("00:00:00.123456", "00:00:00.123456");
-
- assertToStringOfLocalTime("00:00:00.999999", "00:00:00.999999");
- assertToStringOfLocalTime("00:00:00.999999", "00:00:00.999999499"); // 499 NanoSeconds
- assertToStringOfLocalTime("00:00:01", "00:00:00.999999500"); // 500 NanoSeconds
-
- assertToStringOfLocalTime("23:59:59", "23:59:59");
-
- assertToStringOfLocalTime("23:59:59.999999", "23:59:59.999999");
- assertToStringOfLocalTime("23:59:59.999999", "23:59:59.999999499"); // 499 NanoSeconds
- assertToStringOfLocalTime("24:00:00", "23:59:59.999999500"); // 500 NanoSeconds
- assertToStringOfLocalTime("24:00:00", "23:59:59.999999999"); // 999 NanoSeconds
+ assertToStringOfLocalTime("00:00:00");
+ assertToStringOfLocalTime("00:00:00.1");
+ assertToStringOfLocalTime("00:00:00.12");
+ assertToStringOfLocalTime("00:00:00.123");
+ assertToStringOfLocalTime("00:00:00.1234");
+ assertToStringOfLocalTime("00:00:00.12345");
+ assertToStringOfLocalTime("00:00:00.123456");
+
+ assertToStringOfLocalTime("00:00:00.999999");
+ assertToStringOfLocalTime("00:00:00.999999", "00:00:00.999999499", "499 NanoSeconds round down");
+ assertToStringOfLocalTime("00:00:01", "00:00:00.999999500", "500 NanoSeconds round up");
+
+ assertToStringOfLocalTime("23:59:59");
+
+ assertToStringOfLocalTime("23:59:59.999999");
+ assertToStringOfLocalTime("23:59:59.999999", "23:59:59.999999499", "499 NanoSeconds round down");
+ assertToStringOfLocalTime("24:00:00", "23:59:59.999999500", "500 NanoSeconds round up");
+ assertToStringOfLocalTime("24:00:00", "23:59:59.999999999", "999 NanoSeconds round up");
}
- private void assertToStringOfLocalTime(String expectedOutput, String inputTime) {
- assertEquals("timestampUtils.toString(LocalTime.parse(" + inputTime + "))",
+ private void assertToStringOfLocalTime(String inputTime) {
+ assertToStringOfLocalTime(inputTime, inputTime, null);
+ }
+
+ private void assertToStringOfLocalTime(String expectedOutput, String inputTime, String message) {
+ assertEquals(
+ "timestampUtils.toString(LocalTime.parse(" + inputTime + "))"
+ + (message == null ? ": " + message : ""),
expectedOutput,
timestampUtils.toString(LocalTime.parse(inputTime)));
}
@Test
public void testToLocalTime() throws SQLException {
- assertToLocalTime("00:00:00", "00:00:00");
-
- assertToLocalTime("00:00:00.1", "00:00:00.1");
- assertToLocalTime("00:00:00.12", "00:00:00.12");
- assertToLocalTime("00:00:00.123", "00:00:00.123");
- assertToLocalTime("00:00:00.1234", "00:00:00.1234");
- assertToLocalTime("00:00:00.12345", "00:00:00.12345");
- assertToLocalTime("00:00:00.123456", "00:00:00.123456");
- assertToLocalTime("00:00:00.999999", "00:00:00.999999");
-
- assertToLocalTime("23:59:59", "23:59:59");
- assertToLocalTime("23:59:59.999999", "23:59:59.999999"); // 0 NanoSeconds
- assertToLocalTime("23:59:59.9999999", "23:59:59.9999999"); // 900 NanoSeconds
- assertToLocalTime("23:59:59.99999999", "23:59:59.99999999"); // 990 NanoSeconds
- assertToLocalTime("23:59:59.999999998", "23:59:59.999999998"); // 998 NanoSeconds
- assertToLocalTime(LocalTime.MAX.toString(), "24:00:00");
+ assertToLocalTime("00:00:00");
+
+ assertToLocalTime("00:00:00.1");
+ assertToLocalTime("00:00:00.12");
+ assertToLocalTime("00:00:00.123");
+ assertToLocalTime("00:00:00.1234");
+ assertToLocalTime("00:00:00.12345");
+ assertToLocalTime("00:00:00.123456");
+ assertToLocalTime("00:00:00.999999");
+
+ assertToLocalTime("23:59:59");
+ assertToLocalTime("23:59:59.999999"); // 0 NanoSeconds
+ assertToLocalTime("23:59:59.9999999"); // 900 NanoSeconds
+ assertToLocalTime("23:59:59.99999999"); // 990 NanoSeconds
+ assertToLocalTime("23:59:59.999999998"); // 998 NanoSeconds
+ assertToLocalTime(LocalTime.MAX.toString(), "24:00:00", "LocalTime can't represent 24:00:00");
+ }
+
+ private void assertToLocalTime(String inputTime) throws SQLException {
+ assertToLocalTime(inputTime, inputTime, null);
}
- private void assertToLocalTime(String expectedOutput, String inputTime) throws SQLException {
- assertEquals("timestampUtils.toLocalTime(" + inputTime + ")",
+ private void assertToLocalTime(String expectedOutput, String inputTime, String message) throws SQLException {
+ assertEquals(
+ "timestampUtils.toLocalTime(" + inputTime + ")"
+ + (message == null ? ": " + message : ""),
LocalTime.parse(expectedOutput),
timestampUtils.toLocalTime(inputTime));
}
View it on GitLab: https://salsa.debian.org/java-team/libpostgresql-jdbc-java/-/compare/27013f2d51f4b555b9d7266e09b2ec78eda0a8b3...7ee8e79514d001b885a7f72170581edada820ac8
--
View it on GitLab: https://salsa.debian.org/java-team/libpostgresql-jdbc-java/-/compare/27013f2d51f4b555b9d7266e09b2ec78eda0a8b3...7ee8e79514d001b885a7f72170581edada820ac8
You're receiving this email because of your account on salsa.debian.org.
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://alioth-lists.debian.net/pipermail/pkg-java-commits/attachments/20220506/a47aa9f7/attachment.htm>
More information about the pkg-java-commits
mailing list